/*****
* fundec.h
* Andy Hammerlindl 2002/8/29
*
* Defines the semantics for defining functions. Both the newexp syntax, and
* the abbreviated C-style function definition.
*****/
#ifndef FUNDEC_H
#define FUNDEC_H
#include "dec.h"
#include "exp.h"
namespace absyntax {
class formal : public absyn {
astType *base;
decidstart *start;
bool Explicit;
varinit *defval;
bool keywordOnly;
struct tySymbolPair : public gc {
absyntax::astType* ty;
symbol sym;
tySymbolPair(absyntax::astType* ty, symbol sym) : ty(ty), sym(sym) {}
};
class formals : public absyn {
//friend class funheader;
mem::list<formal *> fields;
public:
// NOTE: Iterators do NOT include the rest parameter.
auto begin() { return fields.begin(); }
auto end() { return fields.end(); }
auto rbegin() { return fields.rbegin(); }
auto rend() { return fields.rend(); }
private:
formal *rest;
// If the list of formals contains at least one keyword-only formal.
bool keywordOnly;
virtual void prettyprint(ostream &out, Int indent) override;
virtual void add(formal *f) {
if (f->isKeywordOnly()) {
keywordOnly = true;
}
else if (rest) {
em.error(f->getPos());
em << "normal parameter after rest parameter";
}
else if (keywordOnly) {
em.error(f->getPos());
em << "normal parameter after keyword-only parameter";
}
fields.push_back(f);
}
virtual void addRest(formal *f) {
if (rest) {
em.error(f->getPos());
em << "additional rest parameter";
}
else if (f->isKeywordOnly()) {
em.error(f->getPos());
em << "rest parameter declared as keyword-only";
}
rest = f;
}
// Returns the types of each parameter as a signature.
// encodeDefVal means that it will also encode information regarding
// the default values into the signature
types::signature *getSignature(coenv &e,
bool encodeDefVal = false,
bool tacit = false);
// Returns the corresponding function type, assuming it has a return
// value of "result."
types::function *getType(types::ty *result, coenv &e,
bool encodeDefVal = false,
bool tacit = false);
mem::vector<tySymbolPair> *getFields();
virtual void addOps(coenv &e, record *r);
// Add the formal parameters to the environment to prepare for the
// function body's translation.
virtual void trans(coenv &e);