[antlr-interest] C target - initialization of return/scope structures

Cristian Târşoagă cristian.tarsoaga at gmail.com
Thu May 20 00:35:42 PDT 2010


Hi,

I thought about that too :-)
But it won't work, for the same reasons.

They will be wrapped into a scoped structure.
Note that the generated code does not just put MyStruct/smartptr on the
stack...
it will create some antlr_blah_blah_scoped_mystruct which holds
MyStruct/smartptr inside, and that is done using malloc
Since THAT structure will be malloc-ed, MyStruct OR a smartptr inside it
won't be correctly initialized, so I will just get another crash.

  Chris



2010/5/20 <Anders.Karlsson at sybase.com>

>
> Hi,
>
>
> Why don't you just use a smart pointer?
>
>
> myrule
> scope {auto_ptr<MyStruct> s;} //scoped POINTER
> @init{ $myrule::s = auto_ptr<MyStruct>(new MyStruct());} //explicit
> allocation using new
> : rulegoeshere....;
>
> or preferably boost:shared pointer
>
>
> Thank you and kind regards,
> Anders
>
>
>
> Anders Karlsson | Staff SE II, Architect | Sybase Inc, Singapore, ( +65
> 6571 3125 | * anders.karlsson at sybase.com
> -- It takes a tonne of fact to overcome an ounce of opinion
>
>
>
>
>             Cristian Târşoagă
>             <cristian.tarsoag
>             a at gmail.com>                                               To
>             Sent by:                  antlr-interest
>             <antlr-interest-b         <antlr-interest at antlr.org>
>             ounces at antlr.org>                                          cc
>
>                                                                   Subject
>             05/20/2010 03:04          [antlr-interest] C target -
>             PM                        initialization of return/scope
>                                       structures
>
>
>
>
>
>
>
>
>
>
> Hi Jim, that is not my problem, let me show you an example
>
> I want to have a scoped value which is a structure, and my structure holds
> some std::strings
>
> struct MyStruct
> {
>  std::string s1;
>  std::string s2;
> };
>
> //this is part of my grammar
> myrule
> scope {MyStruct s;} //scoped VALUE
> @init{}
> @after{}
> : rulegoeshere....;
>
> As you can see, there is no pointer here, the scoped variable is a 'value'.
> The code generated by antlr creates a scoped wrapper structure that holds
> MyStruct, something like:
>
> ctx->pMyParser_myruleTop = pMyParser_myrulePush(ctx); // this will create a
> wrapper for the scoped value by calling ANTLR3_MALLOC
>
> the wrapper looks like this:
>
> typedef struct  MyParser_myrule_SCOPE_struct
> {
>    void    (ANTLR3_CDECL *free)    (struct MyParser_myrule_SCOPE_struct *
> frame);
>    MyStruct s;
> }
>
> As you can see my struct is inside this structure. The problem is that to
> create the wrapper (see pMyParser_myrulePush above)
> antlr calls ANTLR3_MALLOC (which does malloc of course).
>
> THIS MEANS I'M GONNA GET A CRASH!
>
> Why? because std::string is a c++ class, which HAS to be created/destroyed
> using new/delete, not malloc/free.
>
> That means, I cannot use a scoped VALUE, I have to use a scoped POINTER
> instead, as suggested here:
>
>
> http://www.mail-archive.com/il-antlr-interest@googlegroups.com/msg02614.html
>
>
>
>
> Suggested Solution 1: local new/delete allocation/deallocation
> ------------------------------
> -----------------------------------------------------------
> So my rule will now look like this:
>
> myrule
> scope {MyStruct* s;} //scoped POINTER
> @init{ $myrule::s = new MyStruct();} //explicit allocation using new
> @after{ delete $myrule::s; } //explicit deallocation using delete
> : rulegoeshere....;
>
> Looks good? Well, I think not!
> Because when the rule fails, the @after action is NOT called, and I'm gonna
> get a nice memory leak.
>
> Solution 1': the scoped wrapper has a member called free that can hold a
> 'deleter', but I couldn't find a way to set that.
>
>
> Suggested Solution2: override antlr macros ANTLR3_MALLOC and ANTLR3_FREE
>
> ------------------------------------------------------------------------------------------------------------------------
>
>
> Nice try, but ANTLR3_MALLOC is currently defined like this:
> #define    ANTLR3_MALLOC(request)                    malloc
> ((size_t)(request))
>
> As you can see, the 'request' argument is a SIZE, not a type, which means
> that if I want to override it to make it use 'new' instead of malloc, I
> cannot use it.
> >From the given size I cannot deduce the type (this could work the other
> way
> around if you change the define, to pass it the type you could get the
> size,
> and it could be possible to override the default way of antlr's
> allocations/deallocations)
>
>
>
> That is my problem and those are the options I have. Maybe with some
> adjustment some of them will work, but right now, I'm not happy with any of
> them: first one leaks, second one is not usable.
>
> Maybe you have some hints for me :-)
>
> Thanks a lot for your answer
>
>   Chris
>
> List: http://www.antlr.org/mailman/listinfo/antlr-interest
> Unsubscribe:
> http://www.antlr.org/mailman/options/antlr-interest/your-email-address
>
>
>
>
> List: http://www.antlr.org/mailman/listinfo/antlr-interest
> Unsubscribe:
> http://www.antlr.org/mailman/options/antlr-interest/your-email-address
>


More information about the antlr-interest mailing list