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


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

Pointers as error values

Started by"Morten W. Petersen" <morphex@gmail.com>
First post2015-10-19 00:53 -0700
Last post2015-10-22 06:06 +0000
Articles 20 on this page of 80 — 23 participants

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


Contents

  Pointers as error values "Morten W. Petersen" <morphex@gmail.com> - 2015-10-19 00:53 -0700
    Re: Pointers as error values gazelle@shell.xmission.com (Kenny McCormack) - 2015-10-19 08:26 +0000
      Re: Pointers as error values "Morten W. Petersen" <morphex@gmail.com> - 2015-10-19 02:27 -0700
      Re: Pointers as error values Richard Damon <Richard@Damon-Family.org> - 2015-10-19 23:38 -0400
    Re: Pointers as error values jacobnavia <jacob@jacob.remcomp.fr> - 2015-10-19 10:34 +0200
      Re: Pointers as error values "Morten W. Petersen" <morphex@gmail.com> - 2015-10-19 02:29 -0700
      Re: Pointers as error values mark.bluemel@gmail.com - 2015-10-19 05:53 -0700
    Re: Pointers as error values glen herrmannsfeldt <gah@ugcs.caltech.edu> - 2015-10-19 10:00 +0000
    Re: Pointers as error values Jorgen Grahn <grahn+nntp@snipabacken.se> - 2015-10-19 14:00 +0000
    Re: Pointers as error values gwowen <gwowen@gmail.com> - 2015-10-19 08:02 -0700
      Re: Pointers as error values James Kuyper <jameskuyper@verizon.net> - 2015-10-19 11:53 -0400
    Re: Pointers as error values Ken Brody <kenbrody@spamcop.net> - 2015-10-19 11:25 -0400
    Re: Pointers as error values supercat@casperkitty.com - 2015-10-19 08:41 -0700
    Re: Pointers as error values Keith Thompson <kst-u@mib.org> - 2015-10-19 08:59 -0700
      Re: Pointers as error values "Morten W. Petersen" <morphex@gmail.com> - 2015-10-21 07:32 +0200
        Re: Pointers as error values Ian Collins <ian-news@hotmail.com> - 2015-10-21 19:17 +1300
          Re: Pointers as error values "Morten W. Petersen" <morphex@gmail.com> - 2015-10-21 08:31 +0200
        Re: Pointers as error values Ben Bacarisse <ben.usenet@bsb.me.uk> - 2015-10-21 12:46 +0100
        Re: Pointers as error values Robert Wessel <robertwessel2@yahoo.com> - 2015-10-21 09:35 -0500
          Re: Pointers as error values Ken Brody <kenbrody@spamcop.net> - 2015-10-21 15:24 -0400
            Re: Pointers as error values glen herrmannsfeldt <gah@ugcs.caltech.edu> - 2015-10-22 05:44 +0000
        Re: Pointers as error values Keith Thompson <kst-u@mib.org> - 2015-10-21 10:41 -0700
          Re: Pointers as error values supercat@casperkitty.com - 2015-10-21 11:28 -0700
        Re: Pointers as error values John Temples <usenet@xargs-spam.com> - 2015-10-21 17:45 +0000
          Re: Pointers as error values James Kuyper <jameskuyper@verizon.net> - 2015-10-21 14:15 -0400
            Re: Pointers as error values "Morten W. Petersen" <morphex@gmail.com> - 2015-10-29 16:59 +0100
              Re: Pointers as error values supercat@casperkitty.com - 2015-10-29 12:35 -0700
                Re: Pointers as error values raltbos@xs4all.nl (Richard Bos) - 2015-10-29 21:45 +0000
                  Re: Pointers as error values "Morten W. Petersen" <morphex@gmail.com> - 2015-10-30 06:09 +0100
                    Re: Pointers as error values Rosario19 <Ros@invalid.invalid> - 2015-10-30 08:59 +0100
                      Re: Pointers as error values Rosario19 <Ros@invalid.invalid> - 2015-10-30 09:07 +0100
                      Re: Pointers as error values Rosario19 <Ros@invalid.invalid> - 2015-10-30 09:38 +0100
                        Re: Pointers as error values Rosario19 <Ros@invalid.invalid> - 2015-10-30 09:40 +0100
                    Re: Pointers as error values Robert Wessel <robertwessel2@yahoo.com> - 2015-10-30 04:56 -0500
                    Re: Pointers as error values Ben Bacarisse <ben.usenet@bsb.me.uk> - 2015-10-30 11:00 +0000
              Re: Pointers as error values Robert Wessel <robertwessel2@yahoo.com> - 2015-10-29 23:48 -0500
                Re: Pointers as error values "Morten W. Petersen" <morphex@gmail.com> - 2015-10-30 11:05 +0100
                  Re: Pointers as error values Richard Damon <Richard@Damon-Family.org> - 2015-10-30 07:45 -0400
                    Re: Pointers as error values Malcolm McLean <malcolm.mclean5@btinternet.com> - 2015-10-30 05:04 -0700
                      Re: Pointers as error values "Morten W. Petersen" <morphex@gmail.com> - 2015-10-30 16:09 +0100
                        Re: Pointers as error values Keith Thompson <kst-u@mib.org> - 2015-10-30 11:16 -0700
                          Re: Pointers as error values glen herrmannsfeldt <gah@ugcs.caltech.edu> - 2015-10-30 20:58 +0000
                            Re: Pointers as error values Eric Sosman <esosman@comcast-dot-net.invalid> - 2015-10-30 17:12 -0400
                            Re: Pointers as error values supercat@casperkitty.com - 2015-10-30 14:54 -0700
                            Re: Pointers as error values Robert Wessel <robertwessel2@yahoo.com> - 2015-10-30 18:48 -0500
                              Re: Pointers as error values glen herrmannsfeldt <gah@ugcs.caltech.edu> - 2015-11-01 04:00 +0000
                                Re: Pointers as error values Robert Wessel <robertwessel2@yahoo.com> - 2015-11-01 01:24 -0500
                          Re: Pointers as error values "Morten W. Petersen" <morphex@gmail.com> - 2015-10-31 20:35 +0100
                            Re: Pointers as error values supercat@casperkitty.com - 2015-10-31 13:33 -0700
                        Re: Pointers as error values Richard Damon <Richard@Damon-Family.org> - 2015-10-30 22:19 -0400
                    Re: Pointers as error values supercat@casperkitty.com - 2015-10-30 08:22 -0700
                  Re: Pointers as error values Geoff <geoff@invalid.invalid> - 2015-10-30 13:11 -0700
                    Re: Pointers as error values Geoff <geoff@invalid.invalid> - 2015-10-30 13:23 -0700
        Re: Pointers as error values Geoff <geoff@invalid.invalid> - 2015-10-21 11:13 -0700
          Re: Pointers as error values Ben Bacarisse <ben.usenet@bsb.me.uk> - 2015-10-21 20:31 +0100
            Re: Pointers as error values Geoff <geoff@invalid.invalid> - 2015-10-22 07:13 -0700
          Re: Pointers as error values "Morten W. Petersen" <morphex@gmail.com> - 2015-10-26 07:16 +0100
            Re: Pointers as error values Jorgen Grahn <grahn+nntp@snipabacken.se> - 2015-10-26 09:37 +0000
        Re: Pointers as error values glen herrmannsfeldt <gah@ugcs.caltech.edu> - 2015-10-22 05:38 +0000
          Re: Pointers as error values Ben Bacarisse <ben.usenet@bsb.me.uk> - 2015-10-22 13:51 +0100
          Re: Pointers as error values Keith Thompson <kst-u@mib.org> - 2015-10-22 08:29 -0700
            Re: Pointers as error values supercat@casperkitty.com - 2015-10-22 09:21 -0700
              Re: Pointers as error values Keith Thompson <kst-u@mib.org> - 2015-10-22 10:52 -0700
                Re: Pointers as error values "Morten W. Petersen" <morphex@gmail.com> - 2015-10-26 07:20 +0100
                  Re: Pointers as error values Keith Thompson <kst-u@mib.org> - 2015-10-26 08:09 -0700
                    Re: Pointers as error values supercat@casperkitty.com - 2015-10-26 08:40 -0700
                    Re: Pointers as error values glen herrmannsfeldt <gah@ugcs.caltech.edu> - 2015-10-26 20:02 +0000
                      Re: Pointers as error values supercat@casperkitty.com - 2015-10-26 13:56 -0700
            Re: Pointers as error values glen herrmannsfeldt <gah@ugcs.caltech.edu> - 2015-10-22 21:58 +0000
              Re: Pointers as error values James Kuyper <jameskuyper@verizon.net> - 2015-10-22 19:12 -0400
              Re: Pointers as error values asetofsymbols@gmail.com - 2015-10-22 18:36 -0700
                Re: Pointers as error values asetofsymbols@gmail.com - 2015-10-29 12:47 -0700
    Re: Pointers as error values Lőrinczy Zsigmond <nospam@for.me> - 2015-10-20 17:06 +0200
      Re: Pointers as error values Ben Bacarisse <ben.usenet@bsb.me.uk> - 2015-10-20 19:45 +0100
        Re: Pointers as error values supercat@casperkitty.com - 2015-10-20 14:19 -0700
          Re: Pointers as error values glen herrmannsfeldt <gah@ugcs.caltech.edu> - 2015-10-21 05:28 +0000
            Re: Pointers as error values supercat@casperkitty.com - 2015-10-21 05:48 -0700
              Re: Pointers as error values glen herrmannsfeldt <gah@ugcs.caltech.edu> - 2015-10-22 05:52 +0000
            Re: Pointers as error values Ken Brody <kenbrody@spamcop.net> - 2015-10-21 15:19 -0400
              Re: Pointers as error values glen herrmannsfeldt <gah@ugcs.caltech.edu> - 2015-10-22 06:06 +0000

Page 1 of 4  [1] 2 3 4  Next page →


#73265 — Pointers as error values

From"Morten W. Petersen" <morphex@gmail.com>
Date2015-10-19 00:53 -0700
SubjectPointers as error values
Message-ID<bb26d1c2-246b-45cd-8434-583530881c88@googlegroups.com>
Hi.

I was thinking the other day, that NULL pointers indicate an error.  That got me
wondering, is it possible to use a low number range as valid error indicators?

That is, could for example numbers from 1 to 7 be safely used as error indicators
from a function that should return a pointer?

-Morten

[toc] | [next] | [standalone]


#73267

Fromgazelle@shell.xmission.com (Kenny McCormack)
Date2015-10-19 08:26 +0000
Message-ID<n029fh$jib$1@news.xmission.com>
In reply to#73265
In article <bb26d1c2-246b-45cd-8434-583530881c88@googlegroups.com>,
Morten W. Petersen <morphex@gmail.com> wrote:
>Hi.
>
>I was thinking the other day, that NULL pointers indicate an error.
>That got me wondering, is it possible to use a low number range as
>valid error indicators?
>
>That is, could for example numbers from 1 to 7 be safely used as error
>indicators from a function that should return a pointer?
>
>-Morten

Not according to the C standard - and any minute now, hordes of angry CLC
regs will tell you all about UB and stuff.

But I have seen at least one POSIX function do this - that is, to return
something like:

    (something *) -1

as a flag value.  I've also done it in my own code.

-- 
Windows 95 n. (Win-doze): A 32 bit extension to a 16 bit user interface for
an 8 bit operating system based on a 4 bit architecture from a 2 bit company
that can't stand 1 bit of competition.

Modern day upgrade --> Windows XP Professional x64: Windows is now a 64 bit
tweak of a 32 bit extension to a 16 bit user interface for an 8 bit
operating system based on a 4 bit architecture from a 2 bit company that
can't stand 1 bit of competition.

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


#73269

From"Morten W. Petersen" <morphex@gmail.com>
Date2015-10-19 02:27 -0700
Message-ID<4782c18a-6239-4be3-a2d9-97e3f484f787@googlegroups.com>
In reply to#73267
On Monday, October 19, 2015 at 10:26:32 AM UTC+2, Kenny McCormack wrote:
> In article <bb26d1c2-246b-45cd-8434-583530881c88@googlegroups.com>,
> Morten W. Petersen <morphex@gmail.com> wrote:
> >Hi.
> >
> >I was thinking the other day, that NULL pointers indicate an error.
> >That got me wondering, is it possible to use a low number range as
> >valid error indicators?
> >
> >That is, could for example numbers from 1 to 7 be safely used as error
> >indicators from a function that should return a pointer?
[...]
> 
> Not according to the C standard - and any minute now, hordes of angry CLC
> regs will tell you all about UB and stuff.

I was thinking it might start up some hefty discussions, and that a practical
approach could be found.

> But I have seen at least one POSIX function do this - that is, to return
> something like:
> 
>     (something *) -1
> 
> as a flag value.  I've also done it in my own code.

OK.

-Morten

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


#73374

FromRichard Damon <Richard@Damon-Family.org>
Date2015-10-19 23:38 -0400
Message-ID<YGiVx.68777$Wh7.80@fx07.iad>
In reply to#73267
On 10/19/15 4:26 AM, Kenny McCormack wrote:
> In article <bb26d1c2-246b-45cd-8434-583530881c88@googlegroups.com>,
> Morten W. Petersen <morphex@gmail.com> wrote:
>> Hi.
>>
>> I was thinking the other day, that NULL pointers indicate an error.
>> That got me wondering, is it possible to use a low number range as
>> valid error indicators?
>>
>> That is, could for example numbers from 1 to 7 be safely used as error
>> indicators from a function that should return a pointer?
>>
>> -Morten
>
> Not according to the C standard - and any minute now, hordes of angry CLC
> regs will tell you all about UB and stuff.
>
> But I have seen at least one POSIX function do this - that is, to return
> something like:
>
>      (something *) -1
>
> as a flag value.  I've also done it in my own code.
>

An implementation is allowed to define that it works, but isn't required to.

POSIX, being a standard can define it, in effect forcing the 
implementation that chooses to support POSIX to define it.

It will likely work on many modern implementations, but can make things 
tricky to check in a strictly conforming manner.

What can be done is define the error codes as values of preprocessor 
macros. These can be defined to be 'dummy' objects on machines you don't 
know to support the number casted to pointers, or numbers casted to the 
pointers on machines you know it does work.

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


#73268

Fromjacobnavia <jacob@jacob.remcomp.fr>
Date2015-10-19 10:34 +0200
Message-ID<n029r7$2r7$1@dont-email.me>
In reply to#73265
Le 19/10/2015 09:53, Morten W. Petersen a écrit :
> Hi.
>
> I was thinking the other day, that NULL pointers indicate an error.  That got me
> wondering, is it possible to use a low number range as valid error indicators?
>
> That is, could for example numbers from 1 to 7 be safely used as error indicators
> from a function that should return a pointer?
>
> -Morten
>


Problem:

if (ptr != NULL) ptr->field = 67;

This will not work... You will have to write:

if (ptr != NULL && ptr != (void *)7)

or

if (ptr > (void *)7)

Not very good. I would use return values instead.

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


#73271

From"Morten W. Petersen" <morphex@gmail.com>
Date2015-10-19 02:29 -0700
Message-ID<34910059-1013-4afc-8a0e-c7a2e542782d@googlegroups.com>
In reply to#73268
On Monday, October 19, 2015 at 10:34:56 AM UTC+2, jacobnavia wrote:
[...]
> 
> Problem:
> 
> if (ptr != NULL) ptr->field = 67;
> 
> This will not work... You will have to write:
> 
> if (ptr != NULL && ptr != (void *)7)
> 
> or
> 
> if (ptr > (void *)7)
> 
> Not very good. I would use return values instead.

OK.  I like the second solution, it is somewhat elegant.  But I guess for this
to be a reliable solution, one or more targeted, simple tests have to be 
included to be sure it actually works on the target it is compiled on.

-Morten

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


#73286

Frommark.bluemel@gmail.com
Date2015-10-19 05:53 -0700
Message-ID<ef9cb2ad-f75b-4a9b-84e6-58e01e3e8e94@googlegroups.com>
In reply to#73268
On Monday, 19 October 2015 09:34:56 UTC+1, jacobnavia  wrote:
> Le 19/10/2015 09:53, Morten W. Petersen a écrit :
> > Hi.
> >
> > I was thinking the other day, that NULL pointers indicate an error.  That got me
> > wondering, is it possible to use a low number range as valid error indicators?
> >
> > That is, could for example numbers from 1 to 7 be safely used as error indicators
> > from a function that should return a pointer?
> >
> > -Morten
> >
> 
> 
> Problem:
> 
> if (ptr != NULL) ptr->field = 67;
> 
> This will not work... You will have to write:
> 
> if (ptr != NULL && ptr != (void *)7)
> 
> or
> 
> if (ptr > (void *)7)
> 
> Not very good. I would use return values instead.

Are you sure that pointers can be compared safely in this way? It looks like an assumed flat memory model...

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


#73272

Fromglen herrmannsfeldt <gah@ugcs.caltech.edu>
Date2015-10-19 10:00 +0000
Message-ID<n02evj$vfd$1@speranza.aioe.org>
In reply to#73265
Morten W. Petersen <morphex@gmail.com> wrote:

(snip)
> I was thinking the other day, that NULL pointers indicate an error.  

Often NULL pointers are not an error, such as the end of a linked list.

> That got me wondering, is it possible to use a low number range 
> as valid error indicators?

Not in standard C, but it likely works with many C implementations.
 
> That is, could for example numbers from 1 to 7 be safely used as 
> error indicators from a function that should return a pointer?

In one of my early C programs I was using strstr() to find a 
position in a string. I was used to the PL/I INDEX function
returning an offset, so I subtracted the string pointer from 
the return value. That worked well, except when strstr() returned
NULL.  So, I compared the result to NULL-s where s was the pointer
subtracted.  But that program only had to work one time. 


-- glen

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


#73293

FromJorgen Grahn <grahn+nntp@snipabacken.se>
Date2015-10-19 14:00 +0000
Message-ID<slrnn29trt.5q5.grahn+nntp@frailea.sa.invalid>
In reply to#73265
On Mon, 2015-10-19, Morten W. Petersen wrote:
> Hi.
>
> I was thinking the other day, that NULL pointers indicate an error.  That got me
> wondering, is it possible to use a low number range as valid error indicators?
>
> That is, could for example numbers from 1 to 7 be safely used as error indicators
> from a function that should return a pointer?

If this is for your XML parser library, and passing errors back to the
calling code, then I think it's much nicer if the caller passes around
a "parser instance" struct or object:

  struct ParserContect ctx;
  ...
  if(!parser_feed(&ctx, buf, len)) {
      // parser failed; display an error message
      fprintf(stderr, "XML parser failed on file %s: %s\n",
              filename,
              parser_strerr(&ctx));
  }

Those kinds of errors tend to end up as a message to the user anyway;
there's nothing that the calling code can do with errors 1--7 except
to report them and dump the problem in the human user's lap.

And if you want to pass more info about the error (such as line
numbers) there's room for that too.

/Jorgen

-- 
  // Jorgen Grahn <grahn@  Oo  o.   .     .
\X/     snipabacken.se>   O  o   .

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


#73299

Fromgwowen <gwowen@gmail.com>
Date2015-10-19 08:02 -0700
Message-ID<f9691975-4af2-4bd4-a1eb-aa916cdf38ee@googlegroups.com>
In reply to#73265
On Monday, October 19, 2015 at 8:54:26 AM UTC+1, Morten W. Petersen wrote:
> Hi.
> 
> I was thinking the other day, that NULL pointers indicate an error.  That got me
> wondering, is it possible to use a low number range as valid error indicators?
> 
> That is, could for example numbers from 1 to 7 be safely used as error indicators
> from a function that should return a pointer?

In general, no. I'm sure Keith will quote you the exact sentence that disallows it. 

Somewhat less uselessly: as long as you have enough control of the environment -- compiler version, virtual memory setup, whatever -- you may be able to guarantee that your error values cannot be used as pointers this can be done.  In fact, the linux kernel does exactly that, using PTR_ERR and IS_ERR macros to encode and test error values as invalid pointer values.

http://geeksww.com/tutorials/operating_systems/linux/tips_and_tricks/some_tricks_used_by_the_linux_kernel.php

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


#73304

FromJames Kuyper <jameskuyper@verizon.net>
Date2015-10-19 11:53 -0400
Message-ID<n033ie$592$1@dont-email.me>
In reply to#73299
On 10/19/2015 11:02 AM, gwowen wrote:
> On Monday, October 19, 2015 at 8:54:26 AM UTC+1, Morten W. Petersen wrote:
>> Hi.
>>
>> I was thinking the other day, that NULL pointers indicate an error.  That got me
>> wondering, is it possible to use a low number range as valid error indicators?
>>
>> That is, could for example numbers from 1 to 7 be safely used as error indicators
>> from a function that should return a pointer?
> 
> In general, no. I'm sure Keith will quote you the exact sentence that disallows it.

I haven't seen a response from Keith yet, so I'll handle it.

The key problem is that numbers from 1 to 7 are not pointer values. They
can be converted to pointer values, for example by using (void*)7.
However, here's what the standard says about such conversions:

"Except as previously specified," (and none of the previous
specifications that it's referring to apply in this case) "the result is
implementation-defined, might not be correctly aligned, might not point
to an entity of the referenced type, and might be a trap
representation." (6.3.2.3p5)

First point: "implementation-defined". That allows, among other
possibilities, that (void*)1 and (void*)7 might produce the same result.
In particular, they might be null pointers.

"not .. correctly aligned" is not a problem, as long as you're
converting to void* or a pointer to a character type, which are not
allowed to have alignment restrictions. If you're using T*, where
_Alignof(T) > 1, then incorrect alignment is a possibility, leading to
undefined behavior.

Second point: "might not point to an entity of the referenced type". The
results of comparing pointers for equality are defined for null pointers
(which only compare equal to other null pointers); for all other
pointers, whether or not two pointers compare equal depends upon whether
they point at the same thing. (6.5.9p6) Because there's no guarantee
that they point at any object, an implementation would be within it's
rights to implement pointer equality comparisons in a way that causes
(void*)1 to compare unequal to itself.

Third point: "a trap representation" means that it might not be a valid
pointer. Attempting to write such a pointer value to a pointer object
has undefined behavior, as does attempting to read such a value from a
pointer object. (6.2.5p5)

Fourth point: you could avoid some of the above problems if you could
convert the pointer back to the original integer value before performing
such comparisons. However, here is everything that the standard says
about such a conversion: "Except as previously specified," (and once
again, none of the previous specifications is applicable in this case)
"the result is implementation-defined. If the result cannot be
represented in the integer type, the behavior is undefined. The result
need not be in the range of values of any integer type."  (6.3.2.3p6)

Note, in particular, that (int)(void*)7 is not guaranteed to be 7. The
typedefs [u]intptr_t are optional, but if they are supported by an
implementation, and if p is a pointer to void, then it is guaranteed
that (void*)(uintptr_t)p == p (7.20.1.4). However, there's no pointer
type for which the inverse operation is guaranteed to be reversible.

What you can do is define a fixed set of objects, one corresponding to
each error code, and return the address of the corresponding object to
indicate that the corresponding error has occurred. As long as you're
defining the objects, it might make sense to store some useful
information in them.
-- 
James Kuyper

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


#73301

FromKen Brody <kenbrody@spamcop.net>
Date2015-10-19 11:25 -0400
Message-ID<n031th$u44$1@dont-email.me>
In reply to#73265
On 10/19/2015 3:53 AM, Morten W. Petersen wrote:
> Hi.
>
> I was thinking the other day, that NULL pointers indicate an error.  That got me
> wondering, is it possible to use a low number range as valid error indicators?
>
> That is, could for example numbers from 1 to 7 be safely used as error indicators
> from a function that should return a pointer?

Such usage would be undefined behavior as far as the C language is 
concerned.  It's likely to "work" on any system you're likely to be coding 
on, but there's no such guarantee.

That said, I have been known to use "(void *)-1L" in some rare instances 
where NULL is a valid return code.

You could use something like:

     extern char Error1, Error2, Error3;
     #define MY_ERROR_1 ( (void *) &Error1 )
     #define MY_ERROR_2 ( (void *) &Error2 )

     ...

     if ( some_error_1 )
         return_value = MY_ERROR_1;
     else if ( some_error_2 )
         return_value = MY_ERROR_2;

     ...

While not a "fixed value", they are guaranteed to be unique, and constant in 
any given run of your program.  (Just make sure that some module, perhaps 
your error handler, defines the Error* variables.)

-- 
Kenneth Brody

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


#73303

Fromsupercat@casperkitty.com
Date2015-10-19 08:41 -0700
Message-ID<6afd72a0-57a5-43f8-857f-61373d50aaac@googlegroups.com>
In reply to#73265
On Monday, October 19, 2015 at 2:54:26 AM UTC-5, Morten W. Petersen wrote:
> That is, could for example numbers from 1 to 7 be safely used as error indicators
> from a function that should return a pointer?

If there are a small number of error conditions, and the thing being pointed
to is not too large, one could write the header file like:

int *get_thingie(whatever);
#define THINGIE_NUM_ERRORS 3
extern const int thingie_errors[THINGIE_NUM_ERRORS];
#define THINGIE_FILE_NOT_FOUND      (thingie_errors+0)
#define THINGIE_INSUFFICIENT_MEMORY (thingie_errors+1)
#define THINGIE_INVALID_FILE_FORMAT (thingie_errors+2)

and include a dummy array thingie_errors within the thingie module.

Then within the main code do something like:

    int result = *get_thingie(whatever);
    if (result == THINGIE_FILE_NOT_FOUND) ...
    else if (result == THINGIE_INSUFFICIENT_MEMORY ) ...
    else if (result == THINGIE_INVALID_FILE_FORMAT ) ...
    else ... Got good thingie

Unfortunately, if one confines oneself to strictly-conforming C, there is
no way to avoid having to check every possible error value individually,
which is apt to be annoying and trouble-prone.

If the program will never be used on any implementation which does not
implement a non-overlapping ranking of all pointers (nearly all modern
implementations do, but some hyper-modern implementations might not)
then the code could be improved by adding a couple more declarations in
the header:

#define THINGIE_FIRST_ERROR   (thingie_errors)
#define THINGIE_LAST_ERROR   (thingie_errors+THINGIE_NUM_ERRORS-1)

and then having the main-line code read:

    int result = *get_thingie(whatever);
    if (result < THINGIE_FIRST_ERROR || result > THINGIE_LAST_ERROR)
       ... result is good
    else
       ... now test for individual error codes.

Much cleaner and nicer if there are many error codes.  Such code would
be reliable on many compilers, but unfortunately there is no Standard-
defined means of identifying which compilers it will work with.  Among
machines that have ever been mainstream the most notable ones upon which
it would fail are segmented-model 8086 and 80286; unfortunately, since
the Standard doesn't say that such code should work even on machines that
could support it effortlessly, there's no way of telling whether a hyper-
modern compiler might decide that since the Standard would allow the
main-line code above to do anything whatsoever if 'result' isn't either
a null reference or a pointer to part of the thingie_errors array, that
code may be simplified to 

    if (result == NULL)
       ... result is good
    else
       ... now test for individual error codes.

thus defeating the whole purpose of the code.

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


#73306

FromKeith Thompson <kst-u@mib.org>
Date2015-10-19 08:59 -0700
Message-ID<lnlhayzw6g.fsf@kst-u.example.com>
In reply to#73265
"Morten W. Petersen" <morphex@gmail.com> writes:
> I was thinking the other day, that NULL pointers indicate an error.
> That got me wondering, is it possible to use a low number range as
> valid error indicators?

A null pointer doesn't necessarily indicate an error.  Sometimes it's a
valid result.

> That is, could for example numbers from 1 to 7 be safely used as error
> indicators from a function that should return a pointer?

Not 100% portably.  A small non-zero integer converted to a pointer
type is unlikely to match a valid pointer value, but there's no
guarantee.  Even accessing an invalid pointer (without dereferencing
it) can have undefined behavior.

If possible, I suggest not trying to store any error code separately
from any pointer value.  A common scheme is:

    int func(char **result);

where the function returns 0 on success and some non-zero error
code on error, with *result (a char*) being set to the value you
want if the function was successful.

If you really do want to use distinguished pointer values other
than NULL to denote errors, you can define them as opaque constants.
The caller can check whether a result is equal to one of the error
values without having to know or care how it's represented.  The C
standard uses this scheme in <signal.h>.  SIG_DFL, SIG_ERR, and
SIG_IGN are macros that expand to expressions of pointer-to-function
type.  A given implementation might define them as small integers
converted to the pointer type if that happens to work for that
implementation.

You can also define static objects of the appropriate type, and
use their addresses as your special pointer value.  The address
of any object is guaranteed to be distinct from the address of any
other object.

-- 
Keith Thompson (The_Other_Keith) kst-u@mib.org  <http://www.ghoti.net/~kst>
Working, but not speaking, for JetHead Development, Inc.
"We must do something.  This is something.  Therefore, we must do this."
    -- Antony Jay and Jonathan Lynn, "Yes Minister"

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


#73450

From"Morten W. Petersen" <morphex@gmail.com>
Date2015-10-21 07:32 +0200
Message-ID<n0781l$lg2$1@speranza.aioe.org>
In reply to#73306
On 19.10.2015 17:59, Keith Thompson wrote:
> "Morten W. Petersen" <morphex@gmail.com> writes:
>> I was thinking the other day, that NULL pointers indicate an error.
>> That got me wondering, is it possible to use a low number range as
>> valid error indicators?
>
> A null pointer doesn't necessarily indicate an error.  Sometimes it's a
> valid result.
>
>> That is, could for example numbers from 1 to 7 be safely used as error
>> indicators from a function that should return a pointer?
>
> Not 100% portably.  A small non-zero integer converted to a pointer
> type is unlikely to match a valid pointer value, but there's no
> guarantee.  Even accessing an invalid pointer (without dereferencing
> it) can have undefined behavior.

Hmm, OK.  That dereferencing wouldn't work was expected, but why would
working with an address value not work?

What is a real-life example where using 1-7 as pointer return values
would not work?

> If you really do want to use distinguished pointer values other
> than NULL to denote errors, you can define them as opaque constants.
> The caller can check whether a result is equal to one of the error
> values without having to know or care how it's represented.  The C
> standard uses this scheme in <signal.h>.  SIG_DFL, SIG_ERR, and
> SIG_IGN are macros that expand to expressions of pointer-to-function
> type.  A given implementation might define them as small integers
> converted to the pointer type if that happens to work for that
> implementation.
>
> You can also define static objects of the appropriate type, and
> use their addresses as your special pointer value.  The address
> of any object is guaranteed to be distinct from the address of any
> other object.

Yes, using static objects is a nice, clean alternative, but would
require checking if each and every of these static objects match.

So far I'd like to go for something like what Jacob suggested earlier,
a simple less-than comparison.

-Morten

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


#73455

FromIan Collins <ian-news@hotmail.com>
Date2015-10-21 19:17 +1300
Message-ID<d8op04Fta2fU7@mid.individual.net>
In reply to#73450
Morten W. Petersen wrote:
> On 19.10.2015 17:59, Keith Thompson wrote:
>>
>> You can also define static objects of the appropriate type, and
>> use their addresses as your special pointer value.  The address
>> of any object is guaranteed to be distinct from the address of any
>> other object.
>
> Yes, using static objects is a nice, clean alternative, but would
> require checking if each and every of these static objects match.

How is that different from checking numerical values?

-- 
Ian Collins

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


#73456

From"Morten W. Petersen" <morphex@gmail.com>
Date2015-10-21 08:31 +0200
Message-ID<n07bfu$s6b$1@speranza.aioe.org>
In reply to#73455
On 21.10.2015 08:17, Ian Collins wrote:
> Morten W. Petersen wrote:
>> On 19.10.2015 17:59, Keith Thompson wrote:
>>>
>>> You can also define static objects of the appropriate type, and
>>> use their addresses as your special pointer value.  The address
>>> of any object is guaranteed to be distinct from the address of any
>>> other object.
>>
>> Yes, using static objects is a nice, clean alternative, but would
>> require checking if each and every of these static objects match.
>
> How is that different from checking numerical values?

You tell me? :)

-Morten

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


#73475

FromBen Bacarisse <ben.usenet@bsb.me.uk>
Date2015-10-21 12:46 +0100
Message-ID<8737x4igup.fsf@bsb.me.uk>
In reply to#73450
"Morten W. Petersen" <morphex@gmail.com> writes:

> On 19.10.2015 17:59, Keith Thompson wrote:
<snip>
>> You can also define static objects of the appropriate type, and
>> use their addresses as your special pointer value.  The address
>> of any object is guaranteed to be distinct from the address of any
>> other object.
>
> Yes, using static objects is a nice, clean alternative, but would
> require checking if each and every of these static objects match.

Not if the returned pointer is to a "discriminated" union and you make
them all have the type member == "XmlError".

<snip>
-- 
Ben.

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


#73486

FromRobert Wessel <robertwessel2@yahoo.com>
Date2015-10-21 09:35 -0500
Message-ID<hl7f2b14v3ulm62cdovg3slu3s7vjanbqo@4ax.com>
In reply to#73450
On Wed, 21 Oct 2015 07:32:40 +0200, "Morten W. Petersen"
<morphex@gmail.com> wrote:

>On 19.10.2015 17:59, Keith Thompson wrote:
>> "Morten W. Petersen" <morphex@gmail.com> writes:
>>> I was thinking the other day, that NULL pointers indicate an error.
>>> That got me wondering, is it possible to use a low number range as
>>> valid error indicators?
>>
>> A null pointer doesn't necessarily indicate an error.  Sometimes it's a
>> valid result.
>>
>>> That is, could for example numbers from 1 to 7 be safely used as error
>>> indicators from a function that should return a pointer?
>>
>> Not 100% portably.  A small non-zero integer converted to a pointer
>> type is unlikely to match a valid pointer value, but there's no
>> guarantee.  Even accessing an invalid pointer (without dereferencing
>> it) can have undefined behavior.
>
>Hmm, OK.  That dereferencing wouldn't work was expected, but why would
>working with an address value not work?
>
>What is a real-life example where using 1-7 as pointer return values
>would not work?


While not 1..7, on the S/360 and descendents, on MVS, there is a
rather vital pointer at location 16, which is *very* heavily used by
both system and application code as the starting point to get to many,
many bits of the other data that might be interesting to the program.

Here's a sample usage, posted yesterday in bit.listserv.ibm-main:


>On 20 Oct 2015 06:20:56 -0700, werner.kuehnel@MANNHEIMER.DE (Werner Kuehnel) wrote:
>
>>Here's a little REXX subroutine to get the values:
>>
>>get4hrAvgMSU: 
>>   MSU_4H = 0 
>>   MSU_GRP = 0 
>>   CVT     = C2d(Storage(10,4))              /* point to CVT     */
>>   RMCT    = C2d(Storage(D2x(CVT+604),4))    /* point to RMCT    */
>>   RCT     = C2d(Storage(D2x(RMCT+228),4))   /* Resource Ctrl Tbl*/
>>   MSU_4H = C2d(Storage(D2x(RCT+196),4))    /* 4 hr MSU average */
>>   MSU_GRP = C2d(Storage(D2x(RCT+28),4))     /* Group Limit      */        
>> 
>>return 


The first 16 bytes of the address space are all addressable, but MVS
doesn't put anything interesting (to the application) there.  In fact
address *zero* is perfectly valid (as it is on many systems), and at
some point MVS will have had to store an interrupt vector there (at
least at real address zero, which may, or may not, match what's in a
virtual address space).

Most more recent OSs have been designed with C in mind, and take some
pains to make addresses in low core unusable, at least on systems with
virtual memory (*nix, for example, usually makes the first page
unaddressable, Windows make the first 64KB unaddressable).

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


#73512

FromKen Brody <kenbrody@spamcop.net>
Date2015-10-21 15:24 -0400
Message-ID<n08om7$qpr$1@dont-email.me>
In reply to#73486
On 10/21/2015 10:35 AM, Robert Wessel wrote:
[...]
> Most more recent OSs have been designed with C in mind, and take some
> pains to make addresses in low core unusable, at least on systems with
> virtual memory (*nix, for example, usually makes the first page
> unaddressable, Windows make the first 64KB unaddressable).

I have seen at least one *nix implementation which makes the first page 
(4K?) of memory all zeros, read-only.  Dereferencing a NULL pointer (for 
read) of any type will return zero, and all of the str*() functions will see 
a NULL pointer as an empty string.  (And attemping to write there will still 
SEGV.)

Whether this is a "good" or "bad" idea is left as an exercise for the reader.

-- 
Kenneth Brody

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


Page 1 of 4  [1] 2 3 4  Next page →

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


csiph-web