Path: utzoo!attcan!uunet!bfmny0!tneff From: tneff@bfmny0.UUCP (Tom Neff) Newsgroups: comp.sys.intel Subject: Re: PLM vs. C for 80286/80386 Keywords: PLM C Message-ID: <14391@bfmny0.UUCP> Date: 9 Jun 89 00:37:13 GMT References: <598@philtis.UUCP> <14381@bfmny0.UUCP> <1765@auspex.auspex.com> <14386@bfmny0.UUCP> <1782@auspex.auspex.com> Reply-To: tneff@bfmny0.UUCP (Tom Neff) Organization: ^ Lines: 69 Summary: Expires: Sender: Followup-To: Distribution: [Talking about jump tables versus elseif's for dense 'case' constructs.] In article <1782@auspex.auspex.com> guy@auspex.auspex.com (Guy Harris) writes: >Try a few more arms; if you make it up to, say, 32 arms, and it *still* >generates an if/then/elseif/then... chain, the compiler is probably >being dumb (but check the cycle counts anyway, just for fun...). If >there is an inflection point, check the cycle counts, etc. to see >whether an if/then/elseif/then... chain makes sense for a number of >arms below the inflection point. If so, perhaps the PL/M compiler is >the wrong one.... [Side note: in a separate posting I confirm that iC-x86 does change to a jump table at the "inflection point" of 6 or more cases. I had tried 3 and 5 before retesting and just plain missed it.] I would make the claim that in critical realtime code it's more important to have *consistent* code generation for things like 4- and 5- and 6- case state machines than it is to try and shave the extra cycle by using a completely different algorithm below (undocumented) N number of cases. That's the kind of thing that riseth up to smite the harried sysprog at JUST the wrong time, like when the boss screaming at you from an overseas conference room where Something Went Wrong. :-) The thing is, if you want an elseif construct you can always CODE ONE YOURSELF in any language. The whole point of DO CASE (PL/M) or switch (C) for dense case lists should be to use something different, i.e. a jump table. PL/M does this perforce because its DO CASE is like 'switch' without 'case' - each simple or compound statement within the DO CASE scope is assumed to handle the next integer value of the control expression starting at 0 -- thus: DO CASE state; ; /* case 0 - shouldn't happen */ DO; /* case 1 - do something */ masterflags.busy = TRUE; val = get$something(x, y, @status); CALL OUTWORD(that$port, val); state = 2; END; DO; /* case 2 - something else */ val = INWORD(this$port); CALL put$something(val, 0122H, @status); state = 3; END; DO; masterflags.busy = FALSE; state = 1; END; END; /* end case */ Thus in PL/M you have the responsibility for coding your own RANGE CHECKS in an example like the above. Let state = 5 and the above code branches off into never-never land. Unfortunately as you maintain a project and add new states to a machine there is no good automated way to compute MAX_STATE for range check purposes. I tend to put padding cases at the end of my DO CASE structures just in "case": ;;;;;;;;;;; /* insurance */ -- You may redistribute this article only to those who may freely do likewise. -- Tom Neff UUCP: ...!uunet!bfmny0!tneff "Truisms aren't everything." Internet: tneff@bfmny0.UU.NET