Modules = {}
class Symtable
- def initialize
+ def initialize()
@builtins = BuiltinSyms
+ @modules = Modules
@scopes = [{}]
end
def scope_stop
@scopes.pop()
end
+
+ def canonical_type(type)
+ return name if not type.is_a? String
+ while type.is_a? String
+ newtype = self[type]
+ raise "unknown type #{type}" if newtype.nil?
+ raise "#{type} is not a type (kind: #{type[:kind]})" if (type[:kind] != :type)
+ type = newtype
+ end
+ type
+ end
end
class Lexer
else
error("invalid symbol definition")
end
- if api_only && sym[:export] then
+ if api_only then
sym[:value] = nil
+ sym = nil if not sym[:export]
end
- @symbols[sym[:name]] = sym
+ @symbols[sym[:name]] = sym if sym
end
@symbols
end
while keepGoing(level)
consume()
infixRule = getRule(@prev)[:infix]
-# break if infixRule.nil? # Is this needed?
ast = send(infixRule, ast)
end
ast
@declares = {}
@definitions = {}
add_file(path, api_only)
- type_check
end
def add_file(path, api_only = false)
parse = Parser.new(path)
@name = parse.module()
@imports = parse.imports()
+ @definitions = {}
@imports.each do |m|
next if Modules[m]
- pkg = Package.new("lib/#{m.downcase}.m", api_only = true)
+ pkg = Package.new("lib/#{m.downcase}.m", true)
Modules[pkg.name] = pkg.definitions()
+ @definitions[pkg.name] = {
+ kind: :module,
+ type: :module
+ }
end
- @definitions = parse.definitions(api_only)
+ @definitions.merge!(parse.definitions(api_only))
end
def dump
})
end
- def type_check
+ def generate()
end
end
+##############################
+# Code Generation
+##############################
+
pkg = Package.new("lib/main.m")
-#pp Modules
-#pkg.dump()
+syms = Symtable.new()
+pkg.definitions.each do |name, val|
+ next if val[:kind] == :module
+# pp val
+ type = syms.canonical_type(val[:type])
+ puts name + " ->"
+ pp type
+end