Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]


Groups > comp.lang.c > #15193 > unrolled thread

Exception propagation in C

Started byJames Harris <james.harris.1@googlemail.com>
First post2011-12-29 09:52 -0800
Last post2012-02-17 22:38 +0000
Articles 20 on this page of 73 — 20 participants

Back to article view | Back to comp.lang.c


Contents

  Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2011-12-29 09:52 -0800
    Re: Exception propagation in C jacob navia <jacob@spamsink.net> - 2011-12-29 19:40 +0100
      Re: Exception propagation in C BGB <cr88192@hotmail.com> - 2011-12-29 14:03 -0600
    Re: Exception propagation in C BGB <cr88192@hotmail.com> - 2011-12-29 13:07 -0600
      Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2011-12-30 13:38 -0800
        Re: Exception propagation in C BGB <cr88192@hotmail.com> - 2011-12-30 20:24 -0600
          Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-03 02:19 -0800
            Re: Exception propagation in C BGB <cr88192@hotmail.com> - 2012-01-03 14:04 -0600
              Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-04 04:26 -0800
                Re: Exception propagation in C BGB <cr88192@hotmail.com> - 2012-01-06 14:05 -0600
                  Re: Exception propagation in C jacob navia <jacob@spamsink.net> - 2012-01-06 23:54 +0100
                    Re: Exception propagation in C "Ed Coran" <sysdev@new.net> - 2012-01-06 22:24 -0600
                      Re: Exception propagation in C jacob navia <jacob@spamsink.net> - 2012-01-07 09:15 +0100
                        Re: Exception propagation in C "Ed Coran" <sysdev@new.net> - 2012-01-08 23:45 -0600
                    Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-08 12:52 -0800
                  Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-08 14:20 -0800
                    Re: Exception propagation in C jacob navia <jacob@spamsink.net> - 2012-01-09 00:19 +0100
                      Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-08 21:12 -0800
                        Re: Exception propagation in C Scott Wood <scott@buserror.net> - 2012-01-08 23:41 -0600
                          Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-09 11:00 -0800
                            Re: Exception propagation in C Scott Wood <scott@buserror.net> - 2012-01-10 00:42 -0600
                              Re: Exception propagation in C jgk@panix.com (Joe keane) - 2012-01-11 07:40 +0000
                              Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-11 12:59 -0800
                        Re: Exception propagation in C "Ed Coran" <sysdev@new.net> - 2012-01-09 00:05 -0600
                          Re: Exception propagation in C Ian Collins <ian-news@hotmail.com> - 2012-01-09 20:40 +1300
                            Re: Exception propagation in C "Ed Coran" <sysdev@new.net> - 2012-01-09 04:53 -0600
                              Re: Exception propagation in C 88888 Dihedral <dihedral88888@googlemail.com> - 2012-01-09 05:49 -0800
                    Re: Exception propagation in C Scott Wood <scott@buserror.net> - 2012-01-08 17:29 -0600
                      Re: Exception propagation in C jacob navia <jacob@spamsink.net> - 2012-01-09 00:37 +0100
                      Re: Exception propagation in C Nomen Nescio <nobody@dizum.com> - 2012-01-09 11:36 +0100
                        Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-09 11:08 -0800
            Re: Exception propagation in C Scott Wood <scott@buserror.net> - 2012-01-05 01:25 -0600
              Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-05 09:18 -0800
        Re: Exception propagation in C "s_dubrovich@yahoo.com" <s_dubrovich@yahoo.com> - 2011-12-30 21:20 -0800
          Re: Exception propagation in C "Rod Pemberton" <do_not_have@noavailemail.cmm> - 2011-12-31 06:19 -0500
          Re: Exception propagation in C Nick Keighley <nick_keighley_nospam@hotmail.com> - 2012-01-01 10:32 -0800
        Re: Exception propagation in C "Rod Pemberton" <do_not_have@noavailemail.cmm> - 2011-12-31 05:53 -0500
          Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-01 16:30 -0800
            Re: Exception propagation in C "Rod Pemberton" <do_not_have@noavailemail.cmm> - 2012-01-02 01:50 -0500
              Re: Exception propagation in C Scott Wood <scott@buserror.net> - 2012-01-02 02:03 -0600
                Re: Exception propagation in C "Rod Pemberton" <do_not_have@noavailemail.cmm> - 2012-01-02 15:59 -0500
                  Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-03 04:12 -0800
                  Re: Exception propagation in C Scott Wood <scott@buserror.net> - 2012-01-04 23:53 -0600
                    Re: Exception propagation in C "Rod Pemberton" <do_not_have@noavailemail.cmm> - 2012-01-05 06:45 -0500
              Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-03 04:16 -0800
                Re: Exception propagation in C Keith Thompson <kst-u@mib.org> - 2012-01-03 11:50 -0800
        Re: Exception propagation in C Jens Gustedt <jens.gustedt@loria.fr> - 2011-12-31 13:40 +0100
          Re: Exception propagation in C BGB <cr88192@hotmail.com> - 2011-12-31 10:40 -0600
            Re: Exception propagation in C Jens Gustedt <jens.gustedt@loria.fr> - 2012-01-02 16:49 +0100
              Re: Exception propagation in C BGB <cr88192@hotmail.com> - 2012-01-02 13:02 -0600
                Re: Exception propagation in C Dr Nick <3-nospam@temporary-address.org.uk> - 2012-01-02 19:53 +0000
                  Re: Exception propagation in C ImpalerCore <jadill33@gmail.com> - 2012-01-02 13:10 -0800
                Re: Exception propagation in C ImpalerCore <jadill33@gmail.com> - 2012-01-02 12:58 -0800
                Re: Exception propagation in C Jens Gustedt <jens.gustedt@loria.fr> - 2012-01-04 18:01 +0100
                  Re: Exception propagation in C BGB <cr88192@hotmail.com> - 2012-01-06 14:38 -0600
                    Re: Exception propagation in C "Rod Pemberton" <do_not_have@noavailemail.cmm> - 2012-01-06 21:40 -0500
    Re: Exception propagation in C Kaz Kylheku <kaz@kylheku.com> - 2011-12-29 21:02 +0000
      Re: Exception propagation in C jacob navia <jacob@spamsink.net> - 2011-12-30 10:38 +0100
      Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2011-12-30 14:38 -0800
    Re: Exception propagation in C "Rod Pemberton" <do_not_have@noavailemail.cmm> - 2011-12-29 18:37 -0500
    Re: Exception propagation in C "BartC" <bc@freeuk.com> - 2011-12-30 01:07 +0000
      Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2011-12-30 14:07 -0800
    Re: Exception propagation in C Eric Sosman <esosman@ieee-dot-org.invalid> - 2011-12-30 17:53 -0500
      Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-03 03:56 -0800
    Re: Exception propagation in C jgk@panix.com (Joe keane) - 2012-01-02 09:49 +0000
      Re: Exception propagation in C Kleuske <kleuske@nowhere.net> - 2012-01-02 10:51 +0000
        Re: Exception propagation in C "Rod Pemberton" <do_not_have@noavailemail.cmm> - 2012-01-02 16:01 -0500
          Re: Exception propagation in C Kleuske <kleuske@nowhere.net> - 2012-01-03 11:14 +0000
        Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-01-03 03:59 -0800
          Re: Exception propagation in C Kleuske <kleuske@nowhere.net> - 2012-01-03 12:09 +0000
    Re: Exception propagation in C jgk@panix.com (Joe keane) - 2012-01-03 21:25 +0000
      Re: Exception propagation in C James Harris <james.harris.1@googlemail.com> - 2012-02-15 14:24 -0800
        Re: Exception propagation in C jgk@panix.com (Joe keane) - 2012-02-17 22:38 +0000

Page 2 of 4 — ← Prev page 1 [2] 3 4  Next page →


#15678

FromScott Wood <scott@buserror.net>
Date2012-01-10 00:42 -0600
Message-ID<slrnjgnnf0.5i7.scott@snotra.buserror.net>
In reply to#15651
On 2012-01-09, James Harris <james.harris.1@googlemail.com> wrote:
> On Jan 9, 5:41 am, Scott Wood <sc...@buserror.net> wrote:
>
> ...
>
>> >> 2) Accessing that machine word by polling, as you propose can't be done
>> >>     in one instruction since you need the thread ID to be able to access
>> >>     the thread local storage.
>>
>> > No, for option 3 the word is changed on a thread switch. I have
>> > explained this too.
>>
>> And it's been explained to you that "changed on a thread switch" doesn't
>> work unless this is CPU-local storage by some other mechanism.
>
> If you mean your comment four days ago, I did reply. I said that I
> didn't understand what you meant but you said no more. Not what I
> would call 'explained' to me! :-(

Hmm, sorry about that -- I thought I replied, but I can't find it now.  I
may have had the reply open when my computer crashed.  Something in the
Linux kernel branched right into the middle of an instruction (probably
corrupted memory, maybe rotting hardware). :-(

>> More than one thread can be running at the same time -- no switching, no
>> opportunity to swap the magic variable.
>
> I've been puzzling over this. The only thing I can think that might
> cause a problem is multiple threads running in the same address space
> on different CPUs. Is that what you mean?

Yes, that's what I mean.  Swapping on thread switch is only viable for
per-CPU storage, and if the whole point is to have a fixed virtual address,
that means you need a separate MMU context -- which is doable, but at the
point that I'd question whether it's really worthwhile.

A summary of what I recall of the rest of the reply:

> 2. The scheme proposed will work between languages. I don't intend the
> use of many languages but as an example, a Pascal routine could call
> an assembly routine which could call a C routine which could call
> another assembly routine and all of them could follow the same, very
> fast, exception propagation protocol. (More accurately, the point is
> that each would very quickly skip non-exceptions while still handling
> exceptions.)

It won't skip them as quickly as native compiler exception handling -- but
yes, you'd need some glue code around language transitions unless all the
languages involved implement the same exception mechanism (asm could be made
to, others maybe with compiler extensions?).  How often are potentially
cross-language calls made, compared to component-internal calls?

If you need something that works in a wide variety of languages without glue
or other hassle, it sounds like simple return values are the way to go.  You
can combine errors and successful return values as long as they have
disjoint ranges (often negative for errors, non-negative for success), so
for many functions you may not need an extra pointer parameter.  Perhaps you
could stick a full error report struct in true TLS (you wouldn't need to
access it in the no-error case, so it's not as speed-sensitive), but be
careful that such structs can't leak.

>   if (ex = a()) {if (handler(&ex)) return ex;)
>   if (ex = b()) {if (handler(&ex)) return ex;} 

What would go in handler()?  I'd think you'd usually want to make the
decision locally about whether/how to handle or propagate and clean up from
the error.

> 3. It doesn't allow a sticky exception state such as
> 
> a();
> b();
> if (thread_excep) /* An exception occurred in a() or b() */ 

I've only occasionally felt the need to do this -- often I'd want to clean
up differently, or I wouldn't want to call b() if a() failed.

> If I wanted to add a sticky state I suppose I could write
> 
>   if (ex |= b()) ...
> 
> but that puts the OR instruction (and possibly a memory update) into
> the main non-exception processing path so would be slower in the
> normal processing case. 

Doing a load from memory followed by a compare and conditional branch will
also slow down the normal processing case.  A few ORs is well worth
eliminating a bunch of loads.

> I'm not ruling it out completely. It does do away with the goto. 

Don't fear the goto -- it's one of the nicer ways of doing error cleanup in
C that I've seen.  The Linux kernel uses it extensively.

-Scott

[toc] | [prev] | [next] | [standalone]


#15729

Fromjgk@panix.com (Joe keane)
Date2012-01-11 07:40 +0000
Message-ID<jejeea$72q$1@reader1.panix.com>
In reply to#15678
In article <slrnjgnnf0.5i7.scott@snotra.buserror.net>,
Scott Wood  <scott@buserror.net> wrote:
>If you need something that works in a wide variety of languages without glue
>or other hassle, it sounds like simple return values are the way to go.

I guess the goal is to get rid of the compare-and-branch for each
operation?  Then you have C++-style function calls [assume succesful,
then fix things up with funky extra code if there is an error].  I think
if this is too costly you have other problems.

Also the machine already does something a lot like this.  Assume the
branch is not taken, smash it, later fix the machine state back if you
find there was a mistake.

Maybe the real problem is that you have too many function calls?
Refactor the code, or use macros [or use inline], find the can't-fail
operations...

#define FOO_GET_X(FOO, X) ((X) = (FOO) >> 4 & 0x1)
#define FOO_SET_X(FOO, X) ((FOO) |= ((X) & 0x1) << 4)

[toc] | [prev] | [next] | [standalone]


#15766

FromJames Harris <james.harris.1@googlemail.com>
Date2012-01-11 12:59 -0800
Message-ID<f17625a9-31a5-49ef-b858-37dfe2aa3fcc@t13g2000yqg.googlegroups.com>
In reply to#15678
On Jan 10, 6:42 am, Scott Wood <sc...@buserror.net> wrote:

...

> >> And it's been explained to you that "changed on a thread switch" doesn't
> >> work unless this is CPU-local storage by some other mechanism.
>
> > If you mean your comment four days ago, I did reply. I said that I
> > didn't understand what you meant but you said no more. Not what I
> > would call 'explained' to me! :-(
>
> Hmm, sorry about that -- I thought I replied, but I can't find it now.  I
> may have had the reply open when my computer crashed.

...

No worries. Thanks for replying.

...

> > I've been puzzling over this. The only thing I can think that might
> > cause a problem is multiple threads running in the same address space
> > on different CPUs. Is that what you mean?
>
> Yes, that's what I mean.  Swapping on thread switch is only viable for
> per-CPU storage, and if the whole point is to have a fixed virtual address,
> that means you need a separate MMU context -- which is doable, but at the
> point that I'd question whether it's really worthwhile.

To answer I'll have to ditch the term "thread" which I used as it was
something people would be familiar with and instead use the terms I
really use, "task" and "address space." This starts to get into the
detail of the design and could go way off topic so I'll limit the info
to what hopefully will be enough to make sense of the exception-
indicator word which is the point being discussed.

In these terms, an "address space" is hopefully fairly self
explanatory. A "task" is basically a unit of scheduling. Unlike
threads in a process, tasks, by default, do not share resources.

When an address space is supporting just one task there is no
possibility of interference as there's nothing to interfere with.
Another task in another address space would have its own exception
word.

Where tasks execute in different address spaces they cannot interfere
with each other's exception word as it is in different memory. Address
X in one is not the same as address X in another.

Where a single address space supports multiple tasks things get a bit
more interesting.

If the multiple tasks are kept on one CPU they cannot interfere
because the task switcher changes the exception word on a task switch.
This is my preferred model. The address space is kept on one CPU
partly to avoid the cost of transferring updated data between CPU
caches across the system bus.

(In that scenario, although all the tasks in one address space are
restricted to running on one CPU at a time, the other CPUs would not
need to be idle as they could still be busy executing active tasks in
other address spaces.)

What about the final scenario where it really is a good idea to have
multiple tasks in the same address space running concurrently on
different CPUs? I can think of two potential solutions.

1. Use a different address for the exception word on each CPU. This
does involve pinning tasks to CPUs, more specifically the code of
tasks would need to include the specific address assigned for that
CPU. Fortunately my primary execution model uses a very late link step
- data values are resolved at load time - so the task_excep word and
its ilk could be resolved after the CPU has been chosen by the OS.

2. Alternatively, let the tasks share most address space but keep the
task-local data er, local to a CPU. If it would work this sounds quite
attractive.

As mentioned, my preferred option is to keep an address space on one
CPU at a time but the last situation may be resolvable where
necessary. Someone will probably tell me in no uncertain terms if it
is not.

> A summary of what I recall of the rest of the reply:
>
> > 2. The scheme proposed will work between languages. I don't intend the
> > use of many languages but as an example, a Pascal routine could call
> > an assembly routine which could call a C routine which could call
> > another assembly routine and all of them could follow the same, very
> > fast, exception propagation protocol. (More accurately, the point is
> > that each would very quickly skip non-exceptions while still handling
> > exceptions.)
>
> It won't skip them as quickly as native compiler exception handling

That's what I thought at the start but considering the time that might
be needed to establish stack frames that the native exception handler
can unwind I'm having my doubts. A lot possibly depends on how many
try-type blocks there are as to which option would come out on top.

It is a moot point anyway as the original intention was to devise
something that would work in standard C. Changing a compiler or using
any compiler-specific facilities is out of scope.

> -- but
> yes, you'd need some glue code around language transitions unless all the
> languages involved implement the same exception mechanism (asm could be made
> to, others maybe with compiler extensions?).  How often are potentially
> cross-language calls made, compared to component-internal calls?

Not very often, it's true. As a general construct, cross-language
calls are irrelevant. They may be very important for some of what I am
doing, though, where some of the code calls assembly routines. And
they simplify matters by making the interfaces consistent. (If only I
could do similarly for the calling conventions, eh!)

> If you need something that works in a wide variety of languages without glue
> or other hassle, it sounds like simple return values are the way to go.  You
> can combine errors and successful return values as long as they have
> disjoint ranges (often negative for errors, non-negative for success), so
> for many functions you may not need an extra pointer parameter.  Perhaps you
> could stick a full error report struct in true TLS (you wouldn't need to
> access it in the no-error case, so it's not as speed-sensitive), but be
> careful that such structs can't leak.

Yes, an object that explains what went wrong would have to be in true
TLS.

> >   if (ex = a()) {if (handler(&ex)) return ex;)
> >   if (ex = b()) {if (handler(&ex)) return ex;}
>
> What would go in handler()?  I'd think you'd usually want to make the
> decision locally about whether/how to handle or propagate and clean up from
> the error.

The handlers wouldn't need to be the same. They could be the same or
different depending on need.

> > 3. It doesn't allow a sticky exception state such as
>
> > a();
> > b();
> > if (thread_excep) /* An exception occurred in a() or b() */
>
> I've only occasionally felt the need to do this -- often I'd want to clean
> up differently, or I wouldn't want to call b() if a() failed.

True in many cases. I have a piece of code I wrote just the other day
(using the exception word idea) which needed multiple pieces of
memory. It naturally fell out as

  a = mem_alloc...
  b = mem_alloc...
  if (task_excep) goto excep_handler_mem;

Such a form may not be all that uncommon. Obtain a bunch of things
then check for an exception before using them.

(I have issues with what to represent as an exception if more than one
mem_alloc fails, though!)

> > If I wanted to add a sticky state I suppose I could write
>
> >   if (ex |= b()) ...
>
> > but that puts the OR instruction (and possibly a memory update) into
> > the main non-exception processing path so would be slower in the
> > normal processing case.
>
> Doing a load from memory followed by a compare and conditional branch will
> also slow down the normal processing case.  A few ORs is well worth
> eliminating a bunch of loads.

I don't agree with this at all! The exception word will normally load
from cache, L1 cache at that. The branch predictor, because a taken
exception-branch is rare, will predict not taken and the CPU will
carry on with the next instruction (which it already has read-in and
decoded). The sequence

  cmp [task_excep], 0
  jne handler

should thus virtually disappear in the normal processing case.

> > I'm not ruling it out completely. It does do away with the goto.
>
> Don't fear the goto -- it's one of the nicer ways of doing error cleanup in
> C that I've seen.  The Linux kernel uses it extensively.

Someone mentioned that - maybe you. I'm not sure I'd take the Linux
kernel as a good model (I don't like a lot of conditional compilation,
for example) but in general the reaction to my suggestion of using
goto has been far more positive than I expected.

Another thought just occurs to me. Perhaps the above ideas could be
combined so that instead of

  <operation potentially causing an exception>
  if (task_excep) goto handler_x;

we could have in some cases

  <operation potentially causing an exception>
  if (task_excep && handler_x()) return;

though that fails to skip following statements. Another option could
be some variation of

  <operation potentially causing an exception>
  if (task_excep) if (handler_x()) return;

with appropriate else clauses as required. Not sure. Although I
dislike using goto it does express the thought succinctly and if used
consistently would become idiomatic and thus easy to read.

James

[toc] | [prev] | [next] | [standalone]


#15605

From"Ed Coran" <sysdev@new.net>
Date2012-01-09 00:05 -0600
Message-ID<jee02u$2g2$1@speranza.aioe.org>
In reply to#15602
James Harris wrote:
> On Jan 8, 11:19 pm, jacob navia <ja...@spamsink.net> wrote:

>> 1) Many people including me have told you that each thread needs an
>> exception handler, in a multi-threaded environment. It can't be
>> just a machine word somewhere. It must be thread local storage
>
> This is TLS. I stated that in the initial post.

He seems to be limited in his thinking to the existing implementations he 
has seen or read about. I.e., there is no indication of out-of-the-box 
thinking. His dialog seems to hint toward a C++-like implementation of 
exceptions as the be-all and end-all, bottom line, last answer on the 
topic of exception handling, which is like much of the rationale often 
spewed for C++ features: absurd. His last sentence above is obviously 
wrong also.


[toc] | [prev] | [next] | [standalone]


#15606

FromIan Collins <ian-news@hotmail.com>
Date2012-01-09 20:40 +1300
Message-ID<9mvk04F2h6U1@mid.individual.net>
In reply to#15605
On 01/ 9/12 07:05 PM, Ed Coran wrote:
> James Harris wrote:
>> On Jan 8, 11:19 pm, jacob navia<ja...@spamsink.net>  wrote:
>
>>> 1) Many people including me have told you that each thread needs an
>>> exception handler, in a multi-threaded environment. It can't be
>>> just a machine word somewhere. It must be thread local storage
>>
>> This is TLS. I stated that in the initial post.
>
> He seems to be limited in his thinking to the existing implementations he
> has seen or read about. I.e., there is no indication of out-of-the-box
> thinking. His dialog seems to hint toward a C++-like implementation of
> exceptions as the be-all and end-all, bottom line, last answer on the
> topic of exception handling, which is like much of the rationale often
> spewed for C++ features: absurd.

What is the "C++-like implementation of exceptions"?  There are many.

-- 
Ian Collins

[toc] | [prev] | [next] | [standalone]


#15612

From"Ed Coran" <sysdev@new.net>
Date2012-01-09 04:53 -0600
Message-ID<jeegv7$65o$1@speranza.aioe.org>
In reply to#15606
Ian Collins wrote:
> On 01/ 9/12 07:05 PM, Ed Coran wrote:
>> James Harris wrote:
>>> On Jan 8, 11:19 pm, jacob navia<ja...@spamsink.net>  wrote:
>>
>>>> 1) Many people including me have told you that each thread needs an
>>>> exception handler, in a multi-threaded environment. It can't be
>>>> just a machine word somewhere. It must be thread local storage
>>>
>>> This is TLS. I stated that in the initial post.
>>
>> He seems to be limited in his thinking to the existing
>> implementations he has seen or read about. I.e., there is no
>> indication of out-of-the-box thinking. His dialog seems to hint
>> toward a C++-like implementation of exceptions as the be-all and
>> end-all, bottom line, last answer on the topic of exception
>> handling, which is like much of the rationale often spewed for C++
>> features: absurd.
>
> What is the "C++-like implementation of exceptions"?  There are many.

That which behaves, from the language user perspective, not the language 
implementor perspective, like C++ exceptions do. Close enough. It would 
be incorrect (for lack of a better term which escapes me right now) to 
scrutinize what I wrote from a mostly or only detailed implementation 
level instead of some higher level perspective of the behavioral 
characteristics. 

[toc] | [prev] | [next] | [standalone]


#15640

From88888 Dihedral <dihedral88888@googlemail.com>
Date2012-01-09 05:49 -0800
Message-ID<7427770.1608.1326116991971.JavaMail.geo-discussion-forums@prlh23>
In reply to#15612
Ed Coran於 2012年1月9日星期一UTC+8下午6時53分32秒寫道:
> Ian Collins wrote:
> > On 01/ 9/12 07:05 PM, Ed Coran wrote:
> >> James Harris wrote:
> >>> On Jan 8, 11:19 pm, jacob navia<ja...@spamsink.net>  wrote:
> >>
> >>>> 1) Many people including me have told you that each thread needs an
> >>>> exception handler, in a multi-threaded environment. It can't be
> >>>> just a machine word somewhere. It must be thread local storage
> >>>
> >>> This is TLS. I stated that in the initial post.
> >>
> >> He seems to be limited in his thinking to the existing
> >> implementations he has seen or read about. I.e., there is no
> >> indication of out-of-the-box thinking. His dialog seems to hint
> >> toward a C++-like implementation of exceptions as the be-all and
> >> end-all, bottom line, last answer on the topic of exception
> >> handling, which is like much of the rationale often spewed for C++
> >> features: absurd.
> >
> > What is the "C++-like implementation of exceptions"?  There are many.
> 
> That which behaves, from the language user perspective, not the language 
> implementor perspective, like C++ exceptions do. Close enough. It would 
> be incorrect (for lack of a better term which escapes me right now) to 
> scrutinize what I wrote from a mostly or only detailed implementation 
> level instead of some higher level perspective of the behavioral 
> characteristics.

For the error handling in C, one has to think what part can fail fist. 

The  I/O file related part  or the heap allocation part should be
classified as  checked before used. 

Please list all those actions that can be classified as those  to be checked before used first in all programming languages. 

Of course the choking quick sort in the C standard lib
is another one to be checked. 

Now the questions are:
1. how to avoid redundant checks in various functions,
2. if something checked to be ill how to handle these in the run time
efficiently
3. if there are many functions could fail in the run time then 
how to control these possible failures in one's programs efficiently
and completely to build a robust system 

 
 



 

[toc] | [prev] | [next] | [standalone]


#15599

FromScott Wood <scott@buserror.net>
Date2012-01-08 17:29 -0600
Message-ID<slrnjgk9ng.3lb.scott@snotra.buserror.net>
In reply to#15596
On 2012-01-08, James Harris <james.harris.1@googlemail.com> wrote:
> The thing is, the program would not necessarily be loaded at the same
> address in each address space so the RIP-relative offset to a fixed
> location doesn't work. OT but RIP-relative data addressing is bearable
> for reading constants but otherwise is a pretty awful addition, IMHO.

From glancing at its output, it seems GCC is able to make pretty extensive
use of RIP-relative addressing, and not just for constants.

-Scott

[toc] | [prev] | [next] | [standalone]


#15600

Fromjacob navia <jacob@spamsink.net>
Date2012-01-09 00:37 +0100
Message-ID<jed9cm$pni$2@speranza.aioe.org>
In reply to#15599
Le 09/01/12 00:29, Scott Wood a écrit :
> On 2012-01-08, James Harris<james.harris.1@googlemail.com>  wrote:
>> The thing is, the program would not necessarily be loaded at the same
>> address in each address space so the RIP-relative offset to a fixed
>> location doesn't work. OT but RIP-relative data addressing is bearable
>> for reading constants but otherwise is a pretty awful addition, IMHO.
>
>  From glancing at its output, it seems GCC is able to make pretty extensive
> use of RIP-relative addressing, and not just for constants.
>
> -Scott

Using Macintosh OS X you have ONLY RIP addressing! I had to rewrite
most of lcc's backend to make it run there.

Apple has always been fan of relative addressing.

[toc] | [prev] | [next] | [standalone]


#15613

FromNomen Nescio <nobody@dizum.com>
Date2012-01-09 11:36 +0100
Message-ID<4f54079754ea242121b111f3f2ede93f@dizum.com>
In reply to#15599
Scott Wood <scott@buserror.net> wrote:

> From glancing at its output, it seems GCC is able to make pretty extensive
> use of RIP-relative addressing, and not just for constants.
         ^^^

Thanks to Scott now we get the tombstone question! 

[toc] | [prev] | [next] | [standalone]


#15652

FromJames Harris <james.harris.1@googlemail.com>
Date2012-01-09 11:08 -0800
Message-ID<fbf2e6e9-0131-40fa-a293-4542a9cfbcec@p4g2000vbt.googlegroups.com>
In reply to#15613
On Jan 9, 10:36 am, Nomen Nescio <nob...@dizum.com> wrote:
> Scott Wood <sc...@buserror.net> wrote:
> > From glancing at its output, it seems GCC is able to make pretty extensive
> > use of RIP-relative addressing, and not just for constants.
>
>          ^^^
>
> Thanks to Scott now we get the tombstone question!

:-) Nice one - sorry to be burning up the airwaves! Then again, those
who are not interested in a certain topic can just resist the urge to
read posts on it, I hope!

James

[toc] | [prev] | [next] | [standalone]


#15453

FromScott Wood <scott@buserror.net>
Date2012-01-05 01:25 -0600
Message-ID<slrnjgak2v.vdr.scott@snotra.buserror.net>
In reply to#15358
On 2012-01-03, James Harris <james.harris.1@googlemail.com> wrote:
> On Dec 31 2011, 2:24 am, BGB <cr88...@hotmail.com> wrote:
>> On 12/30/2011 3:38 PM, James Harris wrote:
>
> I've snipped the bits about how TLS is generally accessed. Thanks for
> explaining that info. It was new to me.
>
> ...
>
>> > I was thinking of thread_excep being at a fixed location so it could
>> > literally be checked with one instruction:
>>
>> >    cmp [thread_excep], 0
>>
>> if it is a global though, it is not a TLS.
>>
>> otherwise, I guess it would need to be changed around by the scheduler
>> or something (register variables with scheduler, and it saves/restores
>> their values on context switches or something?...).
>
> Yes. The task switcher would include code along the lines of
>
>   push [thread_excep]
>
> for the outgoing task and, for the incoming task,
>
>   pop [thread_excep]
>
> Since the word would be checked many times between task switches this
> is much faster than following a structure off FS or similar.

You'd have to maintain a different set of page tables on each CPU
in order to keep the address constant...

If you want exceptions, why not use a language with exceptions?

If you're OK with explicit error checking, use the return value or a
pointer argument.

-Scott

[toc] | [prev] | [next] | [standalone]


#15468

FromJames Harris <james.harris.1@googlemail.com>
Date2012-01-05 09:18 -0800
Message-ID<7b1a6902-cf12-4d0e-9555-e20895ffb330@w4g2000vbc.googlegroups.com>
In reply to#15453
On Jan 5, 7:25 am, Scott Wood <sc...@buserror.net> wrote:

...

> >> >    cmp [thread_excep], 0

...

> You'd have to maintain a different set of page tables on each CPU
> in order to keep the address constant...

I don't follow. The machine word cannot be shared among processes
executing in parallel. In fact each thread would have to have its own
copy.

> If you want exceptions, why not use a language with exceptions?

1. Exceptions are not the only requirement.

2. The scheme proposed will work between languages. I don't intend the
use of many languages but as an example, a Pascal routine could call
an assembly routine which could call a C routine which could call
another assembly routine and all of them could follow the same, very
fast, exception propagation protocol. (More accurately, the point is
that each would very quickly skip non-exceptions while still handling
exceptions.)

> If you're OK with explicit error checking, use the return value or a
> pointer argument.

This is definitely a possibility. The regularity of calling routines
a() and b() as follows is quite tempting.

  if (ex = a()) {if (handler(&ex)) return ex;)
  if (ex = b()) {if (handler(&ex)) return ex;}

Naturally, handler() would return non-zero if it did not handle the
exception and the normal returns from a() and b() would be &vars.
Perhaps the main things against it are,

1. It adds a parameter to each call. There is the question of whether
a return be added to routines which cannot generate an exception just
to maintain the regularity. The form is not used in system calls or C
library routines and is unfamiliar to many.

2. It wouldn't look quite so regular when the arguments are included.
Nor would it look so neat when many single-line statements had to be
converted to two lines because of the length of the text.

3. It doesn't allow a sticky exception state such as

  a();
  b();
  if (thread_excep) /* An exception occurred in a() or b() */

If I wanted to add a sticky state I suppose I could write

  if (ex |= b()) ...

but that puts the OR instruction (and possibly a memory update) into
the main non-exception processing path so would be slower in the
normal processing case.

I'm not ruling it out completely. It does do away with the goto.

James

[toc] | [prev] | [next] | [standalone]


#15238

From"s_dubrovich@yahoo.com" <s_dubrovich@yahoo.com>
Date2011-12-30 21:20 -0800
Message-ID<f47cf54b-07c6-4896-af3d-d680dbffef5d@p16g2000yqd.googlegroups.com>
In reply to#15233
On Dec 30, 3:38 pm, James Harris <james.harri...@googlemail.com>
wrote:
> On Dec 29, 7:07 pm, BGB <cr88...@hotmail.com> wrote:
>
> > On 12/29/2011 11:52 AM, James Harris wrote:
>
> ...
>
> > > The issue is the desire to have exception propagation using *standard*
> > > C. I'm not talking principally about detecting exceptions but of a way
> > > for nested functions to signal an exception and have that exception
> > > propagate back along the call chain to a function that is set up to
> > > handle it.
>
> > it depends on what exactly one means by "standard".
> > I will assume here "can work with a typical C compiler on a typical
> > target without the need/ability to modify said compiler to make it work".
>
> Yes, that's the intention.
>
> ...
>
> > > * Option 3. The function detecting an exception creates an exception
> > > object and sets an exception type in a thread-specific variable. Any
> > > calling functions, after each call (or group of calls) test that
> > > variable. If non-zero they jump to a local exception handler if there
> > > is one or jump to a return from the current function if not. This does
> > > involve a test and branch for each call but that is very fast (fusible
> > > and single cycle) and it avoids the need for exception handling
> > > context to be pushed and popped. It would also preserve the branch
> > > prediction of calls and returns.
>
> > TLS variables are not standard C (but are supported by MSVC and GCC).
> > potentially though one could implement them as status-getter function
> > calls, which is allowed in standard C.
>
> I can't see TLS as C or not C. Wouldn't TLS be a characteristic of the
> environment in which the C code runs?
>
> ...
>
> > more so, assuming one had TLS variables, one can't typically access them
> > in a single instruction.
>
> I was thinking of thread_excep being at a fixed location so it could
> literally be checked with one instruction:
>
>   cmp [thread_excep], 0
>
> > more typically it is some magic like:
> > mov ecx, [fs:magicOffset]
> > mov edx, [__myVariable_index]
> > mov eax, [ecx+edx*4]
>
> > and eax, eax
> > jnz ...
>
> > on some systems, they amount to an internal function call.
>
> As shown, with static linking
>
>   if (thread_excep)
>
> should compile to
>
>   cmp [thread_excep], 0
>
> > > If set up to do so the exception handler would handle the exception
> > > itself and clear thread_excep. If not or if it decided to propagate
> > > the exception it would return to its caller with the thread_excep word
> > > still holding the exception value. Or it could alter thread_excep and
> > > return.
>
> > unclear how this would work exactly.
>
> I'll try to explain what I have in mind. There would be a machine word
> (which I've called thread_excep above) which would be initialised to
> zero. A non-zero value would be set in it to indicate that an
> exception had occurred. I'm not sure how best to use the word but one
> option is to use different bits to indicate exception classes: data
> exception, index exception, io exception, user exception etc.
>
> In the main body of the code exceptions would be detected by
>
>   if (thread_excep) goto handler_2;
>
> Within a function there would be as many handlers as are needed. Say
> we wanted to deal with only index-type exceptions in this module. We
> could code
>
> handler_2:
>   if (thread_excep & EXCEP_INDEX) {
>     /* Deal with an index exception */
>     thread_excep &= ~EXCEP_INDEX;
>     /* Delete the exception object */
>     /* Next step: return, go on to next iteration, whatever */
>   }
>   else return 0;
>
> In the else path the value of thread_excep has not been changed so
> whatever called this routine will get a chance to handle the
> exception(s).
>
> Does that make sense? I'd welcome corrections or improvements.
>
> James

Yeah, these sound like state flags.  The example is rather abstract
from the problem, so it is hard to suggest C or I.

A couple of decades ago I had a commecial dish service that provided
delayed stock data to a terminal with a serial port which could be
connected to a PC and with commercial software, a screen full of
stock, bond, options, mutual funds and news headlines, could be
followed.  Of course the PC software was an addon expense with a hefty
monthy charge to follow a handful of additional securities above what
the terminal provided.  So I wrote my own in C.

The serial output was the raw data feed at 9600 baud, the data used a
poor man's encryption that wasn't to hard to figure out after snooping
the output.  But the output records for a security could vary from
complete (all the fields of the record were transmitted) to sparse
(one or more 'update' fields were in the stream).  They were 15-20
minute quote delayed, so the vast majority of records were just
partial updates to things like last quote, new high/low, volume, etc.
And the fields would vary by security type, of course.  It was
relatively easy to see that each record transmitted for a 'new'
security started with SOH`byte followed by SecurityNumber`word.  The
word was transmitted little endian as I recall.  There after, various
control codes, like SOH, told for which field or security type, etc.
The SecurityNumber wasn't the cusip number, it was just a sequence
number and the outfit published a directory every so often showing
which number went to which security,  The only help was that
securities were group by number ranges so say bonds were numbers >
50,000.  But there were small number ranges inbetween that were
unassigned also.

My program development was stepwise and somewhat haphazard because I
didn't know, I had to deduce, the data stream.  I wrote this on and
for a PC XT clone that ran at 10mhz, and its serial port card used an
i8250, that's an early model with a one byte tx/rx buffer, so the
handler can't dally or you lose data.

I wrote the C code in two main chunks, part one to handle the input
stream to a ring buffer, and when the status port said RX register was
empty, part 2 extracted data off the ring buffer like a secondary
stream treating non-printables like SOH (control codes) as state flags
within a for(;;) block - those were control codes for the meaning of
the following data in the stream.  That's alot like 'exceptions'
without the overhead in that the input stream is random and not
repeatable. Also a difference is that the control codes were like
trees, one lead to check for a limited number of succession leaves
(controls for individual update fields, if present).

Nowadays you could use threads, one per control codes like SOH to
decode for the next data, but you need a 'sink' thread to catch
undefined or errant data.  In my case with the state flags in the
for(;;) block, I discarded errant and unknown records until I figured
out what they meant, then added in a state flag and handler for them.

I also did something silly, which was to do random writes to my data
file on a ramdisk.  IIRC is was a 256k ramdisk, so the file held only
a small subset of the securities.  Every so often the ram disk data
file would be copied to the hard disk.

It actually worked well with surprisingly few bad records due to data
loss.

I used char flags for the data controls like SOH instead of dealing
with bit shifts to extract control data, so they; ie. SOH_flg, was
either null or non-zero.

Pretty definitely standard C, fwiw, without setjmp, longjmp, raise,
signal or even malloc for that matter.

Good for a chuckle eh?

Steve

[toc] | [prev] | [next] | [standalone]


#15242

From"Rod Pemberton" <do_not_have@noavailemail.cmm>
Date2011-12-31 06:19 -0500
Message-ID<jdmr0m$ntg$1@speranza.aioe.org>
In reply to#15238
<s_dubrovich@yahoo.com> wrote in message
news:f47cf54b-07c6-4896-af3d-d680dbffef5d@p16g2000yqd.googlegroups.com...
>

<way OT for c.l.c, fine for alt.*>

> A couple of decades ago I had a commecial dish service
> that provided delayed stock data ...
> [...]
> They were 15-20 minute quote delayed

Quote feeds are delayed 15 minutes for non-market makers.

> My program development was stepwise and somewhat haphazard
> because I didn't know, I had to deduce, the [stock quote] data stream.

They probably weren't using NASDAQ or NYSE protocols for the
satellite feed.  You weren't subscribed to an official NASDAQ or NYSE quote
feed.  If you had been, you could've gotten the protocols for the quote
stream after you (i.e., your company's legal department) signed a
non-disclosure agreement.  I worked at a brokerage a decade or so ago
programming on their stock trading application and also software for a
couple of their feeds: SOES and SuperSOES (obsolete).  The system had
numerous other computers and related market feeds: quote feeds, market
feeds, alternate markets, ECNs, Instinet, etc.  I was so complicated that no
one knew how it was all connected.  As part of a merger, new management
wanted to know.  It took numerous departments months to obtain all the info
and produce a diagram.  Apparently, they thought they could reduce costs by
replacing the system ... laugh.

> I wrote this on and for a PC XT clone that ran at 10mhz,
> and its serial port card used an i8250, that's an early model
> with a one byte tx/rx buffer, so the handler can't dally
> or you lose data.

That's tough to do on a PC ...  Market volume was probably much less back
then.  I'm assuming this was late 1980's from the PC and dish service.  You
probably weren't getting a full quote feed anyway.  We had mainframes
handling the quote feed data during early 2000's: four T1s.  These T1s were
completely maxed out while the market was open.  After a mistake in our
networking department, we got connected to all the T1's available at the
time for NYSE, all fourteen of them ...  I think it was NYSE, but it may
have been for NASDAQ.  The company relocated around that time to an
adjacent building,  and then we started losing quotes ...  "Where is the
opening quote for security XYZ?"  The extra distance on the rerouted T1s
was causing the data to time out.  That was all about a decade ago when
market volume was much lower than it is today.

> IIRC is was a 256k ramdisk, so the file held only
> a small subset of the securities.

Yes ...

We also used a software ramdisk on the mainframes which had some of the
fastest memory manufactured at the time.  They were considering hardware
ramdisks, but found out the hardware ramdisks used the same memory as in the
mainframes ...  So, they stayed with software ramdisks.

> Every so often the ram disk data
> file would be copied to the hard disk.

Start of day ... end of day.  Batch processing, to produce reports required
for NASDAQ and NYSE, ran from about 8PM to 5AM ...  Another department
burned it all to laser disks to comply with securities and other Federal
laws.  We also had to submit a huge amount of data to another firm that
generated compliance reports.

> Pretty definitely standard C, fwiw, without setjmp, longjmp,
> raise, signal or even malloc for that matter.
>
> Good for a chuckle eh?

Looping works!


Rod Pemberton


[toc] | [prev] | [next] | [standalone]


#15269

FromNick Keighley <nick_keighley_nospam@hotmail.com>
Date2012-01-01 10:32 -0800
Message-ID<27917046-9ddc-40ee-b554-b2bb335f1c75@p13g2000yqd.googlegroups.com>
In reply to#15238
On Dec 31 2011, 5:20 am, "s_dubrov...@yahoo.com"
<s_dubrov...@yahoo.com> wrote:
> On Dec 30, 3:38 pm, James Harris <james.harri...@googlemail.com>
> wrote:
>
>
>
>
>
> > On Dec 29, 7:07 pm, BGB <cr88...@hotmail.com> wrote:
>
> > > On 12/29/2011 11:52 AM, James Harris wrote:
>
> > ...
>
> > > > The issue is the desire to have exception propagation using *standard*
> > > > C. I'm not talking principally about detecting exceptions but of a way
> > > > for nested functions to signal an exception and have that exception
> > > > propagate back along the call chain to a function that is set up to
> > > > handle it.
>
> > > it depends on what exactly one means by "standard".
> > > I will assume here "can work with a typical C compiler on a typical
> > > target without the need/ability to modify said compiler to make it work".
>
> > Yes, that's the intention.
>
> > ...
>
> > > > * Option 3. The function detecting an exception creates an exception
> > > > object and sets an exception type in a thread-specific variable. Any
> > > > calling functions, after each call (or group of calls) test that
> > > > variable. If non-zero they jump to a local exception handler if there
> > > > is one or jump to a return from the current function if not. This does
> > > > involve a test and branch for each call but that is very fast (fusible
> > > > and single cycle) and it avoids the need for exception handling
> > > > context to be pushed and popped. It would also preserve the branch
> > > > prediction of calls and returns.
>
> > > TLS variables are not standard C (but are supported by MSVC and GCC).
> > > potentially though one could implement them as status-getter function
> > > calls, which is allowed in standard C.
>
> > I can't see TLS as C or not C. Wouldn't TLS be a characteristic of the
> > environment in which the C code runs?
>
> > ...
>
> > > more so, assuming one had TLS variables, one can't typically access them
> > > in a single instruction.
>
> > I was thinking of thread_excep being at a fixed location so it could
> > literally be checked with one instruction:
>
> >   cmp [thread_excep], 0
>
> > > more typically it is some magic like:
> > > mov ecx, [fs:magicOffset]
> > > mov edx, [__myVariable_index]
> > > mov eax, [ecx+edx*4]
>
> > > and eax, eax
> > > jnz ...
>
> > > on some systems, they amount to an internal function call.
>
> > As shown, with static linking
>
> >   if (thread_excep)
>
> > should compile to
>
> >   cmp [thread_excep], 0
>
> > > > If set up to do so the exception handler would handle the exception
> > > > itself and clear thread_excep. If not or if it decided to propagate
> > > > the exception it would return to its caller with the thread_excep word
> > > > still holding the exception value. Or it could alter thread_excep and
> > > > return.
>
> > > unclear how this would work exactly.
>
> > I'll try to explain what I have in mind. There would be a machine word
> > (which I've called thread_excep above) which would be initialised to
> > zero. A non-zero value would be set in it to indicate that an
> > exception had occurred. I'm not sure how best to use the word but one
> > option is to use different bits to indicate exception classes: data
> > exception, index exception, io exception, user exception etc.
>
> > In the main body of the code exceptions would be detected by
>
> >   if (thread_excep) goto handler_2;
>
> > Within a function there would be as many handlers as are needed. Say
> > we wanted to deal with only index-type exceptions in this module. We
> > could code
>
> > handler_2:
> >   if (thread_excep & EXCEP_INDEX) {
> >     /* Deal with an index exception */
> >     thread_excep &= ~EXCEP_INDEX;
> >     /* Delete the exception object */
> >     /* Next step: return, go on to next iteration, whatever */
> >   }
> >   else return 0;
>
> > In the else path the value of thread_excep has not been changed so
> > whatever called this routine will get a chance to handle the
> > exception(s).
>
> > Does that make sense? I'd welcome corrections or improvements.
>
> > James
>
> Yeah, these sound like state flags.  The example is rather abstract
> from the problem, so it is hard to suggest C or I.
>
> A couple of decades ago I had a commecial dish service that provided
> delayed stock data to a terminal with a serial port which could be
> connected to a PC and with commercial software, a screen full of
> stock, bond, options, mutual funds and news headlines, could be
> followed.  Of course the PC software was an addon expense with a hefty
> monthy charge to follow a handful of additional securities above what
> the terminal provided.  So I wrote my own in C.
>
> The serial output was the raw data feed at 9600 baud, the data used a
> poor man's encryption that wasn't to hard to figure out after snooping
> the output.  But the output records for a security could vary from
> complete (all the fields of the record were transmitted) to sparse
> (one or more 'update' fields were in the stream).  They were 15-20
> minute quote delayed, so the vast majority of records were just
> partial updates to things like last quote, new high/low, volume, etc.
> And the fields would vary by security type, of course.  It was
> relatively easy to see that each record transmitted for a 'new'
> security started with SOH`byte followed by SecurityNumber`word.  The
> word was transmitted little endian as I recall.  There after, various
> control codes, like SOH, told for which field or security type, etc.
> The SecurityNumber wasn't the cusip number, it was just a sequence
> number and the outfit published a directory every so often showing
> which number went to which security,  The only help was that
> securities were group by number ranges so say bonds were numbers >
> 50,000.  But there were small number ranges inbetween that were
> unassigned also.
>
> My program development was stepwise and somewhat haphazard because I
> didn't know, I had to deduce, the data stream.  I wrote this on and
> for a PC XT clone that ran at 10mhz, and its serial port card used an
> i8250, that's an early model with a one byte tx/rx buffer, so the
> handler can't dally or you lose data.
>
> I wrote the C code in two main chunks, part one to handle the input
> stream to a ring buffer, and when the status port said RX register was
> empty, part 2 extracted data off the ring buffer like a secondary
> stream treating non-printables like SOH (control codes) as state flags
> within a for(;;) block - those were control codes for the meaning of
> the following data in the stream.  That's alot like 'exceptions'
> without the overhead in that the input stream is random and not
> repeatable. Also a difference is that the control codes were like
> trees, one lead to check for a limited number of succession leaves
> (controls for individual update fields, if present).
>
> Nowadays you could use threads, one per control codes like SOH to
> decode for the next data, but you need a 'sink' thread to catch
> undefined or errant data.  In my case with the state flags in the
> for(;;) block, I discarded errant and unknown records until I figured
> out what they meant, then added in a state flag and handler for them.
>
> I also did something silly, which was to do random writes to my data
> file on a ramdisk.  IIRC is was a 256k ramdisk, so the file held only
> a small subset of the securities.  Every so often the ram disk data
> file would be copied to the hard disk.
>
> It actually worked well with surprisingly few bad records due to data
> loss.
>
> I used char flags for the data controls like SOH instead of dealing
> with bit shifts to extract control data, so they; ie. SOH_flg, was
> either null or non-zero.
>
> Pretty definitely standard C, fwiw, without setjmp, longjmp, raise,
> signal or even malloc for that matter.

interesting war story. Um but where are the exceptions? Sounds like a
for(;;) loop with a big switch statement. It's kind of "well,how else
would you write it?"

[toc] | [prev] | [next] | [standalone]


#15241

From"Rod Pemberton" <do_not_have@noavailemail.cmm>
Date2011-12-31 05:53 -0500
Message-ID<jdmpfp$kf1$1@speranza.aioe.org>
In reply to#15233
"James Harris" <james.harris.1@googlemail.com> wrote in message
news:541969d7-e4ab-43ba-8cf5-679f18eb3221@m4g2000vbc.googlegroups.com...
>
> There would be a machine word [...]

He said: "machine word"...  Ok, that screams "volatile" keyword to me.

Are these x86 exceptions or x86 interrupts or events external to C, e.g.,
for your OS, that are being passed to C via a machine word?  I suspect they
are, but you probably wanted to keep things topical for c.l.c. ...

At a minimum, I'd suggest reading Eric Sosman's post and also
my post on a.o.d.  ;-)

You said Kaz's setjmp/longjmp code looks good to you, so I'd take that as an
intuitive proxy that you should use it.  I'm sure others on c.l.c. could
help you fix whatever issues you have with it.


Rod Pemberton

[toc] | [prev] | [next] | [standalone]


#15293

FromJames Harris <james.harris.1@googlemail.com>
Date2012-01-01 16:30 -0800
Message-ID<6c6a43c1-53d3-4386-a156-542d0ac75eb4@p42g2000vbt.googlegroups.com>
In reply to#15241
On Dec 31 2011, 10:53 am, "Rod Pemberton"
<do_not_h...@noavailemail.cmm> wrote:
> "James Harris" <james.harri...@googlemail.com> wrote in message

...

> > There would be a machine word [...]
>
> He said: "machine word"...  Ok, that screams "volatile" keyword to me.

May be a bad term. I mean a 16-bit word on a 16-bit machine, a 32-bit
word on a 32-bit machine, a 64-bit word on a 64-bit machine. I
sometimes avoid the plain term "word" as it has been somewhat hijacked
by the 16-bit brigade. I come from an older era where the word size
depended on the machine.

> Are these x86 exceptions or x86 interrupts or events external to C, e.g.,
> for your OS, that are being passed to C via a machine word?  I suspect they
> are, but you probably wanted to keep things topical for c.l.c. ...

This fully applies to C (or another language for that matter). The
machine word is one that could be set, altered and cleared all in the
language or in a called module whether in the same language or not.
That said, it could just as easily be modified by the OS or something
else. Perhaps you could think of it and the operations as a protocol.
Whatever raises an exception that it doesn't handle itself sets the
word and returns to its caller. Whatever does handle outstanding
exceptions clears the word. And the word is checked whenever
appropriate.

> At a minimum, I'd suggest reading Eric Sosman's post and also
> my post on a.o.d.  ;-)

LOL! You think I wouldn't read all the replies?

> You said Kaz's setjmp/longjmp code looks good to you, so I'd take that as an
> intuitive proxy that you should use it.  I'm sure others on c.l.c. could
> help you fix whatever issues you have with it.

My comment was a general one. It looked like good code but it's not
what I was looking for. In fact I wasn't looking for a solution as
such but for feedback on my preferred option (which I got). Some good
points were made and I have some replies to get round to making.

James

[toc] | [prev] | [next] | [standalone]


#15301

From"Rod Pemberton" <do_not_have@noavailemail.cmm>
Date2012-01-02 01:50 -0500
Message-ID<jdrk0l$i28$1@speranza.aioe.org>
In reply to#15293
"James Harris" <james.harris.1@googlemail.com> wrote in message
news:6c6a43c1-53d3-4386-a156-542d0ac75eb4@p42g2000vbt.googlegroups.com...
> On Dec 31 2011, 10:53 am, "Rod Pemberton"
> <do_not_h...@noavailemail.cmm> wrote:
> > "James Harris" <james.harri...@googlemail.com> wrote in message
...

> > There would be a machine word [...]
>
> > He said: "machine word"... Ok, that screams "volatile" keyword to me.
>
> May be a bad term. I mean a 16-bit word on a 16-bit machine, a 32-bit
> word on a 32-bit machine, a 64-bit word on a 64-bit machine. I
> sometimes avoid the plain term "word" as it has been somewhat hijacked
> by the 16-bit brigade. I come from an older era where the word size
> depended on the machine.
>

[ ... continuing the thought ...]

> > Are these x86 exceptions or x86 interrupts or events external to C,
> > e.g., for your OS, that are being passed to C via a machine word?
> > I suspect they are, but you probably wanted to keep things topical
> > for c.l.c. ...
>
> This fully applies to C (or another language for that matter). The
> machine word is one that could be set, altered and cleared all in the
> language or in a called module whether in the same language or not.
> That said, it could just as easily be modified by the OS or something
> else. Perhaps you could think of it and the operations as a protocol.
> Whatever raises an exception that it doesn't handle itself sets the
> word and returns to its caller. Whatever does handle outstanding
> exceptions clears the word. And the word is checked whenever
> appropriate.

Ok, that screams "volatile" keyword to me.  Anything modified outside of C
and used by C is unknown to C so needs a volatile so it's not optimized away
or to ensure it's reloaded from memory instead of being cached in a register
since it's value could changed by non-C code ...

> > At a minimum, I'd suggest reading Eric Sosman's post and
> > also my post on a.o.d. ;-)
>
> LOL! You think I wouldn't read all the replies?

No.  First, I wasn't sure you were reading from a.o.d.  Second, it was just
easier than saying I didn't agree with some comments of other post-ers
without starting an argument with them.  My experience with c.l.c people
over the past decade is that many of them are insanely hostile, intolerant
of any criticism, and will argue to their death that they are correct when
in fact they are provably wrong ...


Rod Pemberton

[toc] | [prev] | [next] | [standalone]


#15303

FromScott Wood <scott@buserror.net>
Date2012-01-02 02:03 -0600
Message-ID<slrnjg2p6e.dqm.scott@snotra.buserror.net>
In reply to#15301
On 2012-01-02, Rod Pemberton <do_not_have@noavailemail.cmm> wrote:
> "James Harris" <james.harris.1@googlemail.com> wrote in message
> news:6c6a43c1-53d3-4386-a156-542d0ac75eb4@p42g2000vbt.googlegroups.com...
>> On Dec 31 2011, 10:53 am, "Rod Pemberton"
>> <do_not_h...@noavailemail.cmm> wrote:
>> > "James Harris" <james.harri...@googlemail.com> wrote in message
> ...
>> > Are these x86 exceptions or x86 interrupts or events external to C,
>> > e.g., for your OS, that are being passed to C via a machine word?
>> > I suspect they are, but you probably wanted to keep things topical
>> > for c.l.c. ...
>>
>> This fully applies to C (or another language for that matter). The
>> machine word is one that could be set, altered and cleared all in the
>> language or in a called module whether in the same language or not.
>> That said, it could just as easily be modified by the OS or something
>> else. Perhaps you could think of it and the operations as a protocol.
>> Whatever raises an exception that it doesn't handle itself sets the
>> word and returns to its caller. Whatever does handle outstanding
>> exceptions clears the word. And the word is checked whenever
>> appropriate.
>
> Ok, that screams "volatile" keyword to me.  Anything modified outside of C
> and used by C is unknown to C so needs a volatile so it's not optimized away
> or to ensure it's reloaded from memory instead of being cached in a register
> since it's value could changed by non-C code ...

The relevant factor isn't "C" versus "non-C", it's synchronous versus
asynchronous (or perhaps, outside this instance of the single-threaded C
execution model).

If it's modified by code during what the C code sees as an ABI-conformant
function call (which seems to be the case here -- I don't think he was
talking about recovering from hardware exceptions), it doesn't matter what
language the function is implemented in, as long as it is indeed
ABI-conformant -- volatile is not needed.

OTOH, if the variable is modified from an interrupt/signal handler, another
thread, etc. you'll need (at a minimum) either volatile or some
implementation-specific optimization barrier, even if the code that actually
modifies the variable is also written in C.

-Scott

[toc] | [prev] | [next] | [standalone]


Page 2 of 4 — ← Prev page 1 [2] 3 4  Next page →

Back to top | Article view | comp.lang.c


csiph-web