[M3devel] next problem (NT386GNU)
Tony Hosking
hosking at cs.purdue.edu
Tue Jan 22 00:56:27 CET 2008
I should be able to get cm3cg doing the right thing by the end of the
week.
On Jan 21, 2008, at 6:06 PM, Jay wrote:
> I don't want to deal with learning about CVS branches, please.
>
> I can try the __cdecl thunk hack I had nearly working, over in m3-
> win\import-libs.
> It's lame compared to my parse.c though.
>
> Given void __stdcall Foo(int a, struct {int a, b}), or rather Foo 12,
>
> it would generate
>
> one source file/.obj
> void __stdcall F(int a, int b, int c);
> void __stdcall Fstdcall(int a, int b, int c) { return Fstdcall
> (a b c); }
>
> another source file/.obj
> void __stdcall Fstdcall(int a, int b, int c);
> void __cdecl F(int a, int b, int c) { return Fstdcall(a b c); }
>
> If I could put parse.c back, I could limit this to functions that
> take structs.
> Or at least one function in particular that I know is a current
> problem.
> Limiting this hack would be good.
>
> - Jay
>
>
> > CC: m3devel at elegosoft.com
> > From: hosking at cs.purdue.edu
> > Subject: Re: next problem (NT386GNU)
> > Date: Mon, 21 Jan 2008 17:32:32 -0500
> > To: jayk123 at hotmail.com
> >
> > I'd prefer to have the backend do it properly based on properly
> > declared types. I'd prefer to keep this code out of the current
> > mainline of parse.c -- you could fork a temporary branch if
> necessary.
> >
> > On Jan 21, 2008, at 5:16 PM, Jay wrote:
> >
> > > Understood. Put back my parse.c in the meantime?
> > >
> > > Also, the front end could do this, right? And probably without a
> > > stack?
> > > It could compute "effective parameter size" and pass that down.
> > > Backend could then divide by 4 and claim that is the signature,
> > > that number of parameters.
> > >
> > > Would have to see how passing a struct works out anyway -- one
> > > parameter
> > > or one per field.
> > >
> > > - Jay
> > >
> > >
> > > > CC: m3devel at elegosoft.com
> > > > From: hosking at cs.purdue.edu
> > > > Subject: Re: next problem (NT386GNU)
> > > > Date: Mon, 21 Jan 2008 12:01:28 -0500
> > > > To: jayk123 at hotmail.com
> > > >
> > > > I just need to fix m3cc/cm3cg to emit the stdcall parameter
> > > > information for imported procedures. It is simply a matter of
> not
> > > > ignoring declare_param for import_procedure chunks. This means
> > > > maintaining a current_function_decl (and possibly a
> > > > current_param_count) stack (since import_procedure can occur
> > > inside a
> > > > declare_procedure chunk). I know what needs doing, but have
> not much
> > > > free time right now...
> > > >
> > > > On Jan 21, 2008, at 11:10 AM, Jay wrote:
> > > >
> > > > > agreed once I thought about it
> > > > > I guess that explains left to right as well.
> > > > > Parameters are always left to right from a higher level
> point of
> > > > > view, and if that is wrong, the compiler will reorder.
> > > > >
> > > > > "everything" works now
> > > > >
> > > > > - Jay
> > > > >
> > > > >
> > > > >
> > > > > > CC: m3devel at elegosoft.com
> > > > > > From: hosking at cs.purdue.edu
> > > > > > Subject: Re: next problem (NT386GNU)
> > > > > > Date: Mon, 21 Jan 2008 10:54:10 -0500
> > > > > > To: jayk123 at hotmail.com
> > > > > >
> > > > > > Surely, when using the gcc-based backend then we should
> make the
> > > > > > backend handle it. The front end handling it is only need
> for
> > > the
> > > > > > integrated x86 backend.
> > > > > >
> > > > > > On Jan 21, 2008, at 2:43 AM, Jay wrote:
> > > > > >
> > > > > > > I haven't tested a fix but I see the problem.
> > > > > > >
> > > > > > > This function returns a struct.
> > > > > > > There are two struct returning calling conventions.
> > > > > > > In one, the backend handles it. Which includes the backend
> > > knowing
> > > > > > > there is a return value and its type (or at least its
> size?).
> > > > > > > In the other, the front end handles it. In this case, the
> > > front
> > > > > end
> > > > > > > generates passing an extra pointer parameter to the
> > > function, and
> > > > > > > the function's return type is void.
> > > > > > >
> > > > > > > The NT calling conventions, all of them, are marked as
> > > front end
> > > > > > > handling it. I assume that is correct, could check.
> > > > > > > Everything else is marked as back end handling.
> > > > > > >
> > > > > > > Now then, somewhere along the line, gcc figures out
> that the
> > > > > return
> > > > > > > value isn't used here.
> > > > > > > The point of the function call is to see if it
> generates an
> > > > > exception.
> > > > > > >
> > > > > > > Gcc removes the function because its return value isn't
> > > used, and,
> > > > > > > well, somehow it doesn't know about the exceptions here.
> > > I'll have
> > > > > > > to see how "raise" is implemented. I think it's by a
> call to a
> > > > > > > function that gets the jmpbuf from a thread local and
> calls
> > > > > > > longjmp. (Did I mention it is very inefficient?)
> > > > > > >
> > > > > > > There are few possible fixes, but nothing completely
> > > satisfactory
> > > > > > > yet in mind.
> > > > > > >
> > > > > > > One is have parse.c mark all function calls as having side
> > > > > affects.
> > > > > > > This is easy, but overly pessimistic.
> > > > > > > Another is for the front end to mark struct returning
> > > functions as
> > > > > > > having side affects. Better, but still overly pessimistic.
> > > > > > > Another is for the front end to mark any function that can
> > > > > raise as
> > > > > > > having side affects. Getting better still. I don't know
> how
> > > to do
> > > > > > > that but I'll look. This is still a bit overly
> pessimistic,
> > > since
> > > > > > > what you really want to know is, not the function's side
> > > affects,
> > > > > > > but whether or not it raised. If the function is inlined,
> > > the side
> > > > > > > affects could be optimized away, or if there are enough
> > > callers
> > > > > who
> > > > > > > don't care about the side affects to warrant an
> > > optimization, and
> > > > > > > depending on the cost of computing the side affects,
> another
> > > > > > > instance of the function could be made that only raises or
> > > not,
> > > > > but
> > > > > > > no side affects otherwise. This is "advanced"
> optimization the
> > > > > sort
> > > > > > > of which tends never to be implemented.
> > > > > > >
> > > > > > > I think the best option is anything that can raise is
> > > marked as
> > > > > > > having side affects.
> > > > > > > I'll see if I can figure that out.
> > > > > > >
> > > > > > > You can figure this out by looking at m3cgcat -binary <
> > > > > M3File.mc >
> > > > > > > 1.txt on PPC_DARWIN and NT386GNU and comparing.
> > > > > > >
> > > > > > > Maybe marking all or nearly functions as having side
> > > effects isn't
> > > > > > > so bad.
> > > > > > > Or at least anything returning a struct. That gets
> parity with
> > > > > > > other platforms, even if it is a bit pessimistic.
> > > > > > > I think I'll do that, and ignore figuring out if raise is
> > > called
> > > > > > > and using that as a filter.
> > > > > > > The parity angle is good.
> > > > > > >
> > > > > > > The good news for all you Unix lovers :) is this bug is
> > > relatively
> > > > > > > portable to Cygwin.
> > > > > > > True, it is specific to NT386GNU having multiple "calling
> > > > > > > conventions", which no other platform has.
> > > > > > > Which again, jokingly, strikes at the question -- What is
> > > Posix?
> > > > > > > What do you want from Cygwin?
> > > > > > > One thing Cygwin does NOT give you is just one calling
> > > convention,
> > > > > > > alas, this calling convention business stinks. It's not
> > > even an NT
> > > > > > > thing, only an NT386 thing. All the other NT platforms
> had/
> > > have
> > > > > > > only one calling convention.
> > > > > > >
> > > > > > > You can't get far on NT386 without needing to support two
> > > calling
> > > > > > > conventions.
> > > > > > > The "OS" uses mostly __stdcall -- callee pops -- smaller,
> > > faster.
> > > > > > > But anything that is varargs, such as printf -- pretty
> much
> > > must
> > > > > > > use caller pops -- __cdecl.
> > > > > > > As well, __cdecl is the default, so prevalent, and used in
> > > most C
> > > > > > > runtime functions.
> > > > > > > There is also __fastcall that uses like up to two
> registers
> > > for
> > > > > > > parameters.
> > > > > > >
> > > > > > > I have seen a platform in which printf did the pop, and it
> > > > > depended
> > > > > > > on the number/size of parameters matching the format
> > > string. On
> > > > > > > most platforms, printf("", 1, 2, 3, 4) just does nothing,
> > > but on
> > > > > > > that platform, it'd unbalance the stack and crash.
> > > > > > >
> > > > > > > - Jay
> > > > > > >
> > > > > > > From: jayk123 at hotmail.com
> > > > > > > To: hosking at cs.purdue.edu
> > > > > > > CC: m3devel at elegosoft.com
> > > > > > > Subject: next problem (NT386GNU)
> > > > > > > Date: Mon, 21 Jan 2008 05:47:28 +0000
> > > > > > >
> > > > > > > M3File.m3
> > > > > > >
> > > > > > > PROCEDURE IsReadable (path: TEXT): BOOLEAN =
> > > > > > > (* We don't really check for readablitiy, just for
> > > existence *)
> > > > > > > BEGIN
> > > > > > > TRY
> > > > > > > EVAL FS.Status (path); line 82
> > > > > > > RETURN TRUE;
> > > > > > > EXCEPT OSError.E =>
> > > > > > > RETURN FALSE;
> > > > > > > END;
> > > > > > > END IsReadable;
> > > > > > >
> > > > > > > -----LINE 82 -----
> > > > > > > start_call_direct p.25 0 Struct
> > > > > > > load_address v.25 0
> > > > > > > pop_param Addr
> > > > > > > load v.26 0 Addr Addr
> > > > > > > pop_param Addr
> > > > > > > call_direct p.25 Struct
> > > > > > > pop Struct
> > > > > > >
> > > > > > >
> > > > > > >
> > > > > > > I'm guessing you only see an import for the first call on
> > > purpose,
> > > > > > > but I will compare with PPC_DARWIN:
> > > > > > >
> > > > > > > -----LINE 46 -----
> > > > > > > import_procedure FS__Status 2 Struct 0 p.25
> > > > > > > declare_indirect 2078421550 -2078421551
> > > > > > > declare_param _return 4 4 Addr 2078421550 F F 50 v.62
> > > > > > > declare_param p 4 4 Addr 1358456180 F F 50 v.63
> > > > > > > start_call_direct p.25 0 Struct
> > > > > > > load_address v.13 0
> > > > > > > pop_param Addr
> > > > > > > load v.14 0 Addr Addr
> > > > > > > pop_param Addr
> > > > > > > call_direct p.25 Struct
> > > > > > > pop Struct
> > > > > > >
> > > > > > >
> > > > > > > .globl _M3File__IsReadable
> > > > > > > .def _M3File__IsReadable; .scl 2; .type 32; .endef
> > > > > > > _M3File__IsReadable:
> > > > > > > .stabn 68,0,178,LM93-_M3File__IsReadable
> > > > > > > LM93:
> > > > > > > pushl %ebp
> > > > > > > movl %esp, %ebp
> > > > > > > pushl %edi
> > > > > > > pushl %esi
> > > > > > > pushl %ebx
> > > > > > > subl $300, %esp
> > > > > > > LBB15:
> > > > > > > .stabn 68,0,181,LM94-_M3File__IsReadable
> > > > > > > LM94:
> > > > > > > L157:
> > > > > > > movl -280(%ebp), %eax
> > > > > > > andl $0, %eax
> > > > > > > orl $_L_1, %eax
> > > > > > > movl %eax, -280(%ebp)
> > > > > > > movl -284(%ebp), %eax
> > > > > > > andl $0, %eax
> > > > > > > movl %eax, -284(%ebp)
> > > > > > > subl $12, %esp
> > > > > > > leal -288(%ebp), %eax
> > > > > > > pushl %eax
> > > > > > > call _RTHooks__PushEFrame
> > > > > > > addl $16, %esp
> > > > > > > leal -288(%ebp), %eax
> > > > > > > addl $48, %eax
> > > > > > > subl $12, %esp
> > > > > > > pushl %eax
> > > > > > > call __setjmp
> > > > > > > addl $16, %esp
> > > > > > > testb %al, %al
> > > > > > > jne L158
> > > > > > > .stabn 68,0,183,LM95-_M3File__IsReadable
> > > > > > > LM95:
> > > > > > > movl -288(%ebp), %eax
> > > > > > > subl $12, %esp
> > > > > > > pushl %eax
> > > > > > > call _RTHooks__PopEFrame
> > > > > > > addl $16, %esp
> > > > > > > movl $1, -304(%ebp)
> > > > > > > jmp L159
> > > > > > > L158:
> > > > > > > .stabn 68,0,185,LM96-_M3File__IsReadable
> > > > > > > LM96:
> > > > > > > movl $0, -304(%ebp)
> > > > > > > L159:
> > > > > > > LBE15:
> > > > > > > movl -304(%ebp), %eax
> > > > > > > leal -12(%ebp), %esp
> > > > > > > popl %ebx
> > > > > > > popl %esi
> > > > > > > popl %edi
> > > > > > > leave
> > > > > > > ret
> > > > > > >
> > > > > > >
> > > > > > > M3File.IsReadable's call to FS.Status is omitted, all
> files
> > > are
> > > > > > > readable, even if they are not openable, therefore it
> "finds"
> > > > > > > cm3.cfg in the current directory and then fails to open
> it..
> > > > > > >
> > > > > > > later..
> > > > > > > ..Jay
> > > > > > >
> > > > > > > Climb to the top of the charts! Play the word scramble
> > > challenge
> > > > > > > with star power. Play now!
> > > > > > > Shed those extra pounds with MSN and The Biggest Loser!
> Learn
> > > > > more.
> > > > > >
> > > > >
> > > > >
> > > > > Shed those extra pounds with MSN and The Biggest Loser! Learn
> > > more.
> > > >
> > >
> > > Climb to the top of the charts! Play the word scramble challenge
> > > with star power. Play now!
> >
>
> Need to know the score, the latest news, or you need your Hotmail®-
> get your "fix". Check it out.
More information about the M3devel
mailing list