internal TypeDefinition GetDelegateType(FunctionType functionType, string name)
        {
            var @delegate = new DelegateDefinition
            {
                Name         = name + "_func",
                FunctionName = name,
                ReturnType   = GetReturnTypeName(functionType.ReturnType.Type, name),
                Parameters   = functionType.Parameters.Select(GetParameter).ToArray()
            };

            _context.AddUnit(@delegate);

            return(@delegate);
        }
Ejemplo n.º 2
0
        public override bool VisitMethodDecl(Method method)
        {
            if (!base.VisitMethodDecl(method) || !method.IsVirtual || method.Ignore)
            {
                return(false);
            }

            var @params      = method.GatherInternalParams(Driver.Options.IsItaniumLikeAbi, true).ToList();
            var delegateName = GenerateDelegateSignature(@params, method.ReturnType);

            var @delegate = new TypedefDecl
            {
                Name          = delegateName,
                QualifiedType = new QualifiedType(
                    new PointerType(
                        new QualifiedType(
                            new FunctionType
                {
                    CallingConvention = method.CallingConvention,
                    IsDependent       = method.IsDependent,
                    Parameters        = @params,
                    ReturnType        = method.ReturnType
                }))),
                Namespace = namespaceDelegates
            };

            var delegateString   = @delegate.Visit(TypePrinter).Type;
            var existingDelegate = GetExistingDelegate(delegateString);

            if (existingDelegate != null)
            {
                Driver.Delegates.Add(method, existingDelegate);
                return(true);
            }

            existingDelegate = new DelegateDefinition(Driver.Options.OutputNamespace, delegateString);
            Driver.Delegates.Add(method, existingDelegate);
            foreach (var library in Driver.Options.Libraries)
            {
                libsDelegates[library].Add(delegateString, existingDelegate);
            }

            namespaceDelegates.Declarations.Add(@delegate);

            return(true);
        }
Ejemplo n.º 3
0
        public override AstNode Visit(DelegateDefinition node)
        {
            // Use the base class for delegates.
            Structure building = node.GetStructure();

            building.SetBase(currentModule.GetDelegateClass());

            try
            {
                building.FixInheritance();
            }
            catch (ModuleException error)
            {
                Error(node, error.Message);
            }

            return(node);
        }
Ejemplo n.º 4
0
        private DelegateDefinition GetExistingDelegate(Module module, string delegateString)
        {
            if (module.Libraries.Count == 0)
            {
                return(Context.Delegates.Values.FirstOrDefault(t => t.Signature == delegateString));
            }

            DelegateDefinition @delegate = null;

            if (new[] { module }.Union(module.Dependencies).Any(
                    m => libsDelegates.ContainsKey(m) && libsDelegates[m].TryGetValue(
                        delegateString, out @delegate)))
            {
                return(@delegate);
            }

            return(null);
        }
Ejemplo n.º 5
0
        private DelegateDefinition GetExistingDelegate(string delegateString)
        {
            if (Driver.Options.Libraries.Count == 0)
            {
                return(Driver.Delegates.Values.FirstOrDefault(t => t.Signature == delegateString));
            }

            DelegateDefinition @delegate = null;

            if (Driver.Options.Libraries.Union(
                    Driver.Symbols.Libraries.SelectMany(l => l.Dependencies)).Any(
                    l => libsDelegates.ContainsKey(l) &&
                    libsDelegates[l].TryGetValue(delegateString, out @delegate)))
            {
                return(@delegate);
            }

            return(null);
        }
Ejemplo n.º 6
0
        public void Write(DelegateDefinition @delegate)
        {
            WriteSummary(@delegate);
            @delegate.Parameters.ToList().ForEach(x => WriteParam(x, x.Name));
            WriteSummary(@delegate);
            var parameters = GetParameters(@delegate.Parameters);

            WriteLine("[UnmanagedFunctionPointer(CallingConvention.Cdecl)]");
            WriteLine($"public unsafe delegate {@delegate.ReturnType.Name} {@delegate.FunctionName} ({parameters});");

            WriteLine($"public unsafe struct {@delegate.Name}");
            using (BeginBlock())
            {
                WriteLine($"public IntPtr Pointer;");
                Write($"public static implicit operator {@delegate.Name}({@delegate.FunctionName} func) => ");
                Write($"new {@delegate.Name} {{ Pointer = Marshal.GetFunctionPointerForDelegate(func) }};");
                WriteLine();
            }
        }
Ejemplo n.º 7
0
        private DelegateDefinition GetExistingDelegate(IList <string> libraries, string delegateString)
        {
            if (libraries.Count == 0)
            {
                return(Context.Delegates.Values.FirstOrDefault(t => t.Signature == delegateString));
            }

            DelegateDefinition @delegate = null;

            if (libraries.Union(
                    Context.Symbols.Libraries.Where(l => libraries.Contains(l.FileName)).SelectMany(
                        l => l.Dependencies)).Any(l => libsDelegates.ContainsKey(l) &&
                                                  libsDelegates[l].TryGetValue(delegateString, out @delegate)))
            {
                return(@delegate);
            }

            return(null);
        }
Ejemplo n.º 8
0
        public override bool VisitMethodDecl(Method method)
        {
            if (!base.VisitMethodDecl(method) || !method.IsVirtual || method.Ignore)
                return false;

            var @params = method.GatherInternalParams(Context.ParserOptions.IsItaniumLikeAbi, true).ToList();
            var delegateName = GenerateDelegateSignature(@params, method.ReturnType);

            var module = method.TranslationUnit.Module;

            Namespace namespaceDelegates;
            if (namespacesDelegates.ContainsKey(module))
            {
                namespaceDelegates = namespacesDelegates[module];
            }
            else
            {
                namespaceDelegates = new Namespace
                {
                    Name = DelegatesNamespace,
                    Namespace = module.Units.Last()
                };
                namespacesDelegates.Add(module, namespaceDelegates);
            }

            var @delegate = new TypedefDecl
                {
                    Name = delegateName,
                    QualifiedType = new QualifiedType(
                        new PointerType(
                            new QualifiedType(
                                new FunctionType
                                {
                                    CallingConvention = method.CallingConvention,
                                    IsDependent = method.IsDependent,
                                    Parameters = @params,
                                    ReturnType = method.ReturnType
                                }))),
                    Namespace = namespaceDelegates,
                    IsSynthetized = true
                };

            Generator.CurrentOutputNamespace = module.OutputNamespace;
            var delegateString = @delegate.Visit(TypePrinter).Type;
            var existingDelegate = GetExistingDelegate(
                method.TranslationUnit.Module.Libraries, delegateString);

            if (existingDelegate != null)
            {
                Context.Delegates.Add(method, existingDelegate);
                return true;
            }

            existingDelegate = new DelegateDefinition(module.OutputNamespace, delegateString);
            Context.Delegates.Add(method, existingDelegate);

            foreach (var library in module.Libraries)
                libsDelegates[library].Add(delegateString, existingDelegate);

            namespaceDelegates.Declarations.Add(@delegate);

            return true;
        }
Ejemplo n.º 9
0
        public override bool VisitMethodDecl(Method method)
        {
            if (!base.VisitMethodDecl(method) || !method.IsVirtual || method.Ignore)
                return false;

            var @params = method.GatherInternalParams(Driver.Options.IsItaniumLikeAbi, true).ToList();
            var delegateName = GenerateDelegateSignature(@params, method.ReturnType);

            var @delegate = new TypedefDecl
                {
                    Name = delegateName,
                    QualifiedType = new QualifiedType(
                        new PointerType(
                            new QualifiedType(
                                new FunctionType
                                {
                                    CallingConvention = method.CallingConvention,
                                    IsDependent = method.IsDependent,
                                    Parameters = @params,
                                    ReturnType = method.ReturnType
                                }))),
                    Namespace = namespaceDelegates
                };

            var delegateString = @delegate.Visit(TypePrinter).Type;
            var existingDelegate = GetExistingDelegate(delegateString);
            if (existingDelegate != null)
            {
                Driver.Delegates.Add(method, existingDelegate);
                return true;
            }

            existingDelegate = new DelegateDefinition(Driver.Options.OutputNamespace, delegateString);
            Driver.Delegates.Add(method, existingDelegate);
            foreach (var library in Driver.Options.Libraries)
                libsDelegates[library].Add(delegateString, existingDelegate);

            namespaceDelegates.Declarations.Add(@delegate);

            return true;
        }
Ejemplo n.º 10
0
        private void AddDelegatesToDictionary(Declaration decl, Module module)
        {
            CallingConvention callingConvention;
            bool             isDependent = false;
            QualifiedType    returnType;
            List <Parameter> @params;

            if (decl is Method)
            {
                var method = (Method)decl;
                @params           = method.GatherInternalParams(Context.ParserOptions.IsItaniumLikeAbi, true).ToList();
                callingConvention = method.CallingConvention;
                isDependent       = method.IsDependent;
                returnType        = method.ReturnType;
            }
            else
            {
                var param         = (Parameter)decl;
                var funcTypeParam = param.Type.Desugar().GetFinalPointee().Desugar() as FunctionType;
                @params           = funcTypeParam.Parameters;
                callingConvention = funcTypeParam.CallingConvention;
                isDependent       = funcTypeParam.IsDependent;
                returnType        = funcTypeParam.ReturnType;
            }

            var       delegateName = GenerateDelegateSignature(@params, returnType);
            Namespace namespaceDelegates;

            if (namespacesDelegates.ContainsKey(module))
            {
                namespaceDelegates = namespacesDelegates[module];
            }
            else
            {
                Namespace parent = null;
                if (string.IsNullOrEmpty(module.OutputNamespace))
                {
                    var group = module.Units.SelectMany(u => u.Declarations).OfType <Namespace>(
                        ).GroupBy(d => d.Name).Where(g => g.Any(d => d.HasDeclarations)).ToList();
                    if (group.Count == 1)
                    {
                        parent = group.Last().Last();
                    }
                }
                if (parent == null)
                {
                    parent = module.Units.Last();
                }
                namespaceDelegates = new Namespace
                {
                    Name      = DelegatesNamespace,
                    Namespace = parent
                };
                namespacesDelegates.Add(module, namespaceDelegates);
            }

            var @delegate = new TypedefDecl
            {
                Name          = delegateName,
                QualifiedType = new QualifiedType(
                    new PointerType(
                        new QualifiedType(
                            new FunctionType
                {
                    CallingConvention = callingConvention,
                    IsDependent       = isDependent,
                    Parameters        = @params,
                    ReturnType        = returnType
                }))),
                Namespace     = namespaceDelegates,
                IsSynthetized = true,
                Access        = decl is Method ? AccessSpecifier.Private : AccessSpecifier.Public
            };

            var delegateString   = @delegate.Visit(TypePrinter).Type;
            var existingDelegate = GetExistingDelegate(
                module, delegateString);

            if (existingDelegate != null)
            {
                Context.Delegates.Add(decl, existingDelegate);
                return;
            }

            existingDelegate = new DelegateDefinition(module.OutputNamespace, delegateString);
            Context.Delegates.Add(decl, existingDelegate);

            libsDelegates[module].Add(delegateString, existingDelegate);

            namespaceDelegates.Declarations.Add(@delegate);
        }
Ejemplo n.º 11
0
        public override bool VisitMethodDecl(Method method)
        {
            if (!base.VisitMethodDecl(method) || !method.IsVirtual || method.Ignore)
            {
                return(false);
            }

            var @params      = method.GatherInternalParams(Context.ParserOptions.IsItaniumLikeAbi, true).ToList();
            var delegateName = GenerateDelegateSignature(@params, method.ReturnType);

            var module = method.TranslationUnit.Module;

            Namespace namespaceDelegates;

            if (namespacesDelegates.ContainsKey(module))
            {
                namespaceDelegates = namespacesDelegates[module];
            }
            else
            {
                namespaceDelegates = new Namespace
                {
                    Name      = DelegatesNamespace,
                    Namespace = module.Units.Last()
                };
                namespacesDelegates.Add(module, namespaceDelegates);
            }

            var @delegate = new TypedefDecl
            {
                Name          = delegateName,
                QualifiedType = new QualifiedType(
                    new PointerType(
                        new QualifiedType(
                            new FunctionType
                {
                    CallingConvention = method.CallingConvention,
                    IsDependent       = method.IsDependent,
                    Parameters        = @params,
                    ReturnType        = method.ReturnType
                }))),
                Namespace     = namespaceDelegates,
                IsSynthetized = true
            };

            Generator.CurrentOutputNamespace = module.OutputNamespace;
            var delegateString   = @delegate.Visit(TypePrinter).Type;
            var existingDelegate = GetExistingDelegate(
                method.TranslationUnit.Module.Libraries, delegateString);

            if (existingDelegate != null)
            {
                Context.Delegates.Add(method, existingDelegate);
                return(true);
            }

            existingDelegate = new DelegateDefinition(module.OutputNamespace, delegateString);
            Context.Delegates.Add(method, existingDelegate);

            foreach (var library in module.Libraries)
            {
                libsDelegates[library].Add(delegateString, existingDelegate);
            }

            namespaceDelegates.Declarations.Add(@delegate);

            return(true);
        }
Ejemplo n.º 12
0
        public override bool VisitMethodDecl(Method method)
        {
            if (!base.VisitMethodDecl(method) || !method.IsVirtual || method.Ignore)
            {
                return(false);
            }

            var @params      = method.GatherInternalParams(Context.ParserOptions.IsItaniumLikeAbi, true).ToList();
            var delegateName = GenerateDelegateSignature(@params, method.ReturnType);

            var module = method.TranslationUnit.Module;

            Namespace namespaceDelegates;

            if (namespacesDelegates.ContainsKey(module))
            {
                namespaceDelegates = namespacesDelegates[module];
            }
            else
            {
                Namespace parent = null;
                if (string.IsNullOrEmpty(module.OutputNamespace))
                {
                    var group = module.Units.SelectMany(u => u.Declarations).OfType <Namespace>(
                        ).GroupBy(d => d.Name).Where(g => g.Any(d => d.HasDeclarations)).ToList();
                    if (group.Count == 1)
                    {
                        parent = group.Last().Last();
                    }
                }
                if (parent == null)
                {
                    parent = module.Units.Last();
                }
                namespaceDelegates = new Namespace
                {
                    Name      = DelegatesNamespace,
                    Namespace = parent
                };
                namespacesDelegates.Add(module, namespaceDelegates);
            }

            var @delegate = new TypedefDecl
            {
                Name          = delegateName,
                QualifiedType = new QualifiedType(
                    new PointerType(
                        new QualifiedType(
                            new FunctionType
                {
                    CallingConvention = method.CallingConvention,
                    IsDependent       = method.IsDependent,
                    Parameters        = @params,
                    ReturnType        = method.ReturnType
                }))),
                Namespace     = namespaceDelegates,
                IsSynthetized = true,
                Access        = AccessSpecifier.Private
            };

            var delegateString   = @delegate.Visit(TypePrinter).Type;
            var existingDelegate = GetExistingDelegate(
                method.TranslationUnit.Module, delegateString);

            if (existingDelegate != null)
            {
                Context.Delegates.Add(method, existingDelegate);
                return(true);
            }

            existingDelegate = new DelegateDefinition(module.OutputNamespace, delegateString);
            Context.Delegates.Add(method, existingDelegate);

            libsDelegates[module].Add(delegateString, existingDelegate);

            namespaceDelegates.Declarations.Add(@delegate);

            return(true);
        }
Ejemplo n.º 13
0
        public override AstNode Visit(DelegateDefinition node)
        {
            // Parse the generic signature.
            GenericSignature genericSign = node.GetGenericSignature();
            GenericPrototype genProto    = GenericPrototype.Empty;
            PseudoScope      protoScope  = null;

            if (genericSign != null)
            {
                // Visit the generic signature.
                genericSign.Accept(this);

                // Connect the generic prototype.
                genProto = genericSign.GetPrototype();

                // Create the placeholders scope.
                protoScope = new PseudoScope(currentScope, genProto);
                node.SetGenericScope(protoScope);
            }

            // Prevent redefinition.
            ScopeMember old = currentContainer.FindType(node.GetName(), GenericPrototype.Empty);

            if (old != null)
            {
                Error(node, "trying to redefine a delegate.");
            }

            // Create the structure
            MemberFlags flags = node.GetFlags();
            // TODO: Check the flags.
            Class building = new Class(node.GetName(), flags, currentContainer);

            building.SetGenericPrototype(genProto);
            building.Position = node.GetPosition();
            node.SetStructure(building);

            // Add into the current scope.
            if (currentContainer.IsNamespace())
            {
                Namespace space = (Namespace)currentContainer;
                space.AddType(building);
            }
            else if (currentContainer.IsStructure() || currentContainer.IsInterface() || currentContainer.IsClass())
            {
                Structure parent = (Structure)currentContainer;
                parent.AddType(building);
            }
            else
            {
                Error(node, "unexpected place for a delegate.");
            }

            // Register the compute binding delegate.
            if (building.GetFullName() == "Chela.Compute.ComputeBinding")
            {
                currentModule.RegisterComputeBindingDelegate(building);
            }

            return(node);
        }
Ejemplo n.º 14
0
 protected override void VisitDelegateParam(DelegateDefinition @delegate, ParamDefinition param)
 {
     base.VisitDelegateParam(@delegate, param);
     VisitFunctionParam(@delegate, param);
 }
Ejemplo n.º 15
0
 protected override void VisitDelegate(DelegateDefinition @delegate)
 {
     base.VisitDelegate(@delegate);
     VisitFunction(@delegate);
 }
Ejemplo n.º 16
0
 public void Basics()
 {
     DelegateDefinition one = new DelegateDefinition(SomeArbitraryMethod);
     one += SomeOtherArbitraryMethod;
     one(1000);
 }