[comp.unix.sysv386] time

martin@mwtech.UUCP (Martin Weitzel) (05/21/91)

In article <588@sherpa.UUCP> rac@sherpa.UUCP (Roger Cornelius) writes:
[...]
>	long seed = time(0L);
	                 ^^--------- wrong
	           time((long *)0);
	                ^^^^^^^^^--- right

Note that the argument to the time system call is a `long *', aka
pointer to long. Repeat after me: POINTER to long.

But I've seen this too often, even in examples printed in some manuals.
Though I had not much confidence into those particular manuals where
I found it (for reasons that probably aren't of any interrest to the
readers of this group), I'm curious if anybody has ideas from where this
misconception originated.

Or, if you have two minutes and you have some source code from which you
suppose that it contains a time system call, just grep through it and
look if it's done right. I'm always wondering why people can't grasp
the difference between a plain integer, a long and pointers to any of it.
-- 
Martin Weitzel, email: martin@mwtech.UUCP, voice: 49-(0)6151-6 56 83

lothar@tmcsys.UUCP (L. Hirschbiegel) (05/22/91)

In article <1141@mwtech.UUCP> martin@mwtech.UUCP (Martin Weitzel) writes:
>In article <588@sherpa.UUCP> rac@sherpa.UUCP (Roger Cornelius) writes:
>[...]
>>	long seed = time(0L);
>	                 ^^--------- wrong
>	           time((long *)0);
>	                ^^^^^^^^^--- right
>

You're a cousin of "lint", aren't you :-) ?

>Note that the argument to the time system call is a `long *', aka
>pointer to long. 

Ever tried to RTFM for yourself? 

	  NAME
	       time - get time

	  DESCRIPTION
	       The time	system call returns the	value of time in seconds
	       since 00:00:00 Greenwich	Mean Time (GMT), January 1, 1970.

	       If tloc is non-zero, the	return value is	also stored in the
                   ^^^^^^^^^^^
	       location	to which tloc points.

If you still don't understand: I'll help you! 
For this little test program:

main()
{
time(0L);
time((long *)0);
}

the assembler output from my C compiler is:

	.file	"main.c"
gcc_compiled.:
.text
	.align 4
.globl main
main:
	pushl %ebp
	movl %esp,%ebp
	pushl $0
	call time
	pushl $0
	call time
.L1:
	leave
	ret

>Repeat after me: POINTER to long.

Repeat after me: IT DOESN'T MATTER :-)

>I'm always wondering why people can't grasp
>the difference between a plain integer, a long and pointers to any of it.

So do I...

>-- 
>Martin Weitzel, email: martin@mwtech.UUCP, voice: 49-(0)6151-6 56 83

Lothar Hirschbiegel
-- 
-----------------------------------------------
L. Hirschbiegel, AEG - A84, Frankfurt (Germany) 
email: unido!aega84!lh     tel: -49-69-66414316  
-----------------------------------------------

gwyn@smoke.brl.mil (Doug Gwyn) (05/22/91)

In article <1141@mwtech.UUCP> martin@mwtech.UUCP (Martin Weitzel) writes:
>>	long seed = time(0L);
>I'm curious if anybody has ideas from where this misconception originated.

The roots of many such errors are probably unknown even to the original
culprits.

In this particular case, my best guess is that the common "time(0)" usage
was "repaired" during port to a system where it mattered, and the person
doing the repair was thinking merely of the required representation for
the argument to work right, not more abstractly in terms of its type.
You can see this also in the common
	#define	NULL	0L

ckp@grebyn.com (Checkpoint Technologies) (05/22/91)

In article <381@tmcsys.UUCP> lh@aega84.UUCP (L. Hirschbiegel) writes:
>In article <1141@mwtech.UUCP> martin@mwtech.UUCP (Martin Weitzel) writes:
>>In article <588@sherpa.UUCP> rac@sherpa.UUCP (Roger Cornelius) writes:
>>[...]
>>>	long seed = time(0L);
>>	                 ^^--------- wrong
>>	           time((long *)0);
>>	                ^^^^^^^^^--- right
>>
>>Note that the argument to the time system call is a `long *', aka
>>pointer to long. 
>
>Ever tried to RTFM for yourself? 
>
>	  NAME
>	       time - get time
>
>	  DESCRIPTION
>	       The time	system call returns the	value of time in seconds
>	       since 00:00:00 Greenwich	Mean Time (GMT), January 1, 1970.
>
>	       If tloc is non-zero, the	return value is	also stored in the
>                   ^^^^^^^^^^^
>	       location	to which tloc points.

You omitted the SYNOPSIS for time: "time_t time(tloc) time_t *tloc;",
which clearly shows that the argument to time() is a pointer to a
time_t (which BTW is the *real* correct answer).  This man page uses an
archaic style when using the term "non-zero".  Read the FAQ for the whole
poop on NULL and 0; there is a place in C where 0 is treated as
NULL, but arguments to functions sans prototype isn't one of them.

>For this little test program:
>
>main()
>{
>time(0L);
>time((long *)0);
>}
>
>the assembler output from my C compiler is:
> [ omitted; irrelevant ]

BIG mistake.  The assembly language output from the C compiler shows all
the implementation details, including the ones which are not guanteed to
be portable.  You will not learn portable C programming this way, quite
the opposite.  There's no favor from anyone in comp.lang.c for
arguing how widely applicable implementation details are; all the
world's NOT a VAX or i386...

>>Repeat after me: POINTER to long.
>Repeat after me: IT DOESN'T MATTER :-)

Too many programmers repeat after you as it is.  It does matter.
-- 
Richard Krehbiel, private citizen      ckp@grebyn.com
(Who needs a fancy .signature?)

jeff@uf.msc.umn.edu (Jeff Turner) (05/22/91)

In article <1141@mwtech.UUCP> martin@mwtech.UUCP (Martin Weitzel) writes:
>In article <588@sherpa.UUCP> rac@sherpa.UUCP (Roger Cornelius) writes:
>[...]
>>	long seed = time(0L);
>	                 ^^--------- wrong
>	           time((long *)0);
>	                ^^^^^^^^^--- right
>
>Note that the argument to the time system call is a `long *', aka
>pointer to long. Repeat after me: POINTER to long.

You are right -- to ensure portability, you should always pass what is expected
(i.e. a pointer and not a long).  This way, if someday a machine is created 
on which a pointer to a long is a different size then a long, the program will
still work.  However, I don't know of any machines on which the two differ.

Perhaps you are confusing time(0) with time(0L).  Calling time(0) on a 16-bit
machine (e.g. PCs not running 386 UNIX) will push only a 16 bit value onto the
stack instead of the 32 bit address that time() is expecting (and is going to
use).  Since half of the 32-bit address will have a random (and probably
non-zero) value, time() will use it as an address to store the current time
into, and bash your memory or cause range-error core-dump.

I encountered this problem frequently back when I was running uPort's SysV/AT.
I found that passing NULL to time() (or to any other similar function) worked
in all cases as the value of NULL changes with the memory model (i.e. small
memory model defined it simply as 0, whereas large memory model defined it
as 0L).  Of course by definition, passing (long*)0 is the only truely correct
way to pass a long pointer that points to address 0, but that is toooooooo
much to type :-)

-Jeff
---
Jeff Turner                           EMAIL: jeff@msc.edu
Minnesota Supercomputer Center, Inc.  VOICE: (612) 626-0544
Minneapolis, Minnesota  55415           FAX: (612) 624-6550

tim@dell.co.uk (Tim Wright) (05/22/91)

In <381@tmcsys.UUCP> lothar@tmcsys.UUCP (L. Hirschbiegel) writes:

>In article <1141@mwtech.UUCP> martin@mwtech.UUCP (Martin Weitzel) writes:
>>In article <588@sherpa.UUCP> rac@sherpa.UUCP (Roger Cornelius) writes:
>>[...]
>>>	long seed = time(0L);
>>	                 ^^--------- wrong
>>	           time((long *)0);
>>	                ^^^^^^^^^--- right
>>

>You're a cousin of "lint", aren't you :-) ?

>>Note that the argument to the time system call is a `long *', aka
>>pointer to long. 

>Ever tried to RTFM for yourself? 

>	  NAME
>	       time - get time

>	  DESCRIPTION
>	       The time	system call returns the	value of time in seconds
>	       since 00:00:00 Greenwich	Mean Time (GMT), January 1, 1970.

>	       If tloc is non-zero, the	return value is	also stored in the
>                   ^^^^^^^^^^^
>	       location	to which tloc points.

>If you still don't understand: I'll help you! 
>For this little test program:

Yes but it's a pointer i.e. they are talking about a non-zero or non-null
pointer. If the compiler allows prototypes, it can cast a 0 correctly.
Without prototypes it cannot.

>main()
>{
>time(0L);
>time((long *)0);
>}

>the assembler output from my C compiler is:
...
irrelevant :-)

>>Repeat after me: POINTER to long.

>Repeat after me: IT DOESN'T MATTER :-)

*WRONG* *WRONG* *WRONG*. Just because it doesn't happen to matter on
*YOUR* machine with *YOUR* C compiler does not mean it does not matter.
On a non-ansi compliant compiler on a '286 system it is possible to
choose a memory model where sizeof(long) != sizeof(long *).
In this case the code generated will be somewhat different :-)

Tim
-- 
Tim Wright, Dell Computer Corp., Bracknell    |  Domain: tim@dell.co.uk
Berkshire, UK, RG12 1RW. Tel: +44-344-860456  |  Uucp: ...!ukc!delluk!tim
Smoke me a Kipper, I'll be back for breakfast - Red Dwarf

david@sco.COM (David Fiander) (05/22/91)

In article <381@tmcsys.UUCP> lh@aega84.UUCP (L. Hirschbiegel) writes:
>
>You're a cousin of "lint", aren't you :-) ?
>

No, he's somebody that knows the difference between a null pointer and
the integer zero.

>Ever tried to RTFM for yourself? 
>
>	  NAME
>	       time - get time
>
>	  DESCRIPTION
>	       The time	system call returns the	value of time in seconds
>	       since 00:00:00 Greenwich	Mean Time (GMT), January 1, 1970.

You missed a line which appears in _my_ FM:

	long *tloc;


>If you still don't understand: I'll help you! 
>For this little test program:
>
>main()
>{
>time(0L);
>time((long *)0);
>}
>
>the assembler output from my C compiler is:
>
> [assembler code deleted,  I try to avoid it]
>

So you're using GCC on an intel platform (i386 obviously, it wouldn't fit
on anything else).

Lucky you, you've never had to program an Cyber 180.  If you tried that
trick on any CDC machine , you would get a "Ring-0" hardware exception
and, if you hadn't installed a handler, your program could get blown off
(I think.  I never used NOS/VE, and what I used just caused a disgusting
penalty hit, since we trapped to the OS, it said "shithead programmer,"
and returned).

There exist architectures on which the NULL pointer is different from
"all bits 0".  In fact, if you can get the compiler people to agree to
it, the best value for the NULL pointer is something that is an invalid
virtual memory address, because then, when somebody tries to dereference
it, you get a core dump (note that 0 might be a valid address which would
never be referred to by the user, for example: the address of the C
startup code).  The large part of a project I was involved was spent
inserting necessary casts into function calls, in order to _fix_ code
written by people that believed 

>
>Repeat after me: IT DOESN'T MATTER :-)

--
David J. Fiander
SCO MMDF Development Team
SCO Canada, Inc.

clewis@ferret.ocunix.on.ca (Chris Lewis) (05/22/91)

In article <381@tmcsys.UUCP> lh@aega84.UUCP (L. Hirschbiegel) writes:
>In article <1141@mwtech.UUCP> martin@mwtech.UUCP (Martin Weitzel) writes:
>>In article <588@sherpa.UUCP> rac@sherpa.UUCP (Roger Cornelius) writes:
>>[...]
>>>	long seed = time(0L);
>>	                 ^^--------- wrong
>>	           time((long *)0);
>>	                ^^^^^^^^^--- right

>Ever tried to RTFM for yourself? 

>	  DESCRIPTION
>	       The time	system call returns the	value of time in seconds
>	       since 00:00:00 Greenwich	Mean Time (GMT), January 1, 1970.

>	       If tloc is non-zero, the	return value is	also stored in the
>                   ^^^^^^^^^^^
>	       location	to which tloc points.

You omitted the part where it defined time as:

	long time (long *tloc)

(Or, for that matter, "time_t time (time_t *tloc);")

Within context, the "non-zero" really means "non-null pointer to long(time_t)"

[I've even seen manual pages where they are out-and-out wrong.  I've
seen time(0) in some manual pages, and that won't work either]

>If you still don't understand: I'll help you! 
>For this little test program:

Lothar goes on to "prove" his point by test compiling a bit of C
and showing that "time(0L)" and "time((long *) 0)" compiles the same
way.  (on what looks like a 386 according to the assembler)

You're lucky.  Not all machines have pointers that are the same length
as longs.  Try this code on a PDP-11 or on many small mode 8086 compilers:

int func(a, b, c)
long *b; int a,c; {
	printf("%d:%d\n", a, c);
}

func(4, 0L, 4);

It won't print "4:4".  Some compilers will print "4:0", and some'll print "0:4",
and some will print garbage.

func(4, (long*)0, 4) will print 4:4.

Lint and Martin are correct.  Pointers aren't longs.  They ain't ints
either.

Didn't your math teacher tell you that you can't prove a theory on a single
example?  On the other hand, any theory can be disproved by a single
counter-example.
-- 
Chris Lewis, Phone: (613) 832-0541, Domain: clewis@ferret.ocunix.on.ca
UUCP: ...!cunews!latour!ecicrl!clewis; Ferret Mailing List:
ferret-request@eci386; Psroff (not Adobe Transcript) enquiries:
psroff-request@eci386 or Canada 416-832-0541.  Psroff 3.0 in c.s.u soon!

ed@mtxinu.COM (Ed Gould) (05/22/91)

>You are right -- to ensure portability, you should always pass what is expected
>(i.e. a pointer and not a long).  This way, if someday a machine is created 
>on which a pointer to a long is a different size then a long, the program will
>still work.  However, I don't know of any machines on which the two differ.

The machine on which this stuff was first developed - the PDP-11 - is
one.  It has 16-bit pointers.  So does any machine with a 64K address
space.  In fact, the early (Sixth Edition and before) form of the time()
call was

	time(t)
	int t[2];

In those days, "long" ints were represented explicitly as arrays
of two ints.  The time() function took (a pointer to) one of those.
It had no meaningful return value.

In Seventh Edition UNIX, by which time the C language had been
extended to include longs and typedefs, time() became

	time_t time(t)
	time_t *t;

Not too long ago, I saw a piece of code (in a large, now commercial,
software system that will remain nameless) that looked like this:

		time_t now;
	#if some_machine_type || some_other_machine_type
		now = time(0);
	#else
		now = time();
	#endif

Evidently, time() failed on those machines when passed no arguments,
so somebody "fixed" the bug.  I wish people would take the 15 or 20
seconds it takes to get something like this right.
-- 
Ed Gould			No longer formally affiliated with,
ed@mtxinu.COM			and certainly not speaking for, mt Xinu.

"I'll fight them as a woman, not a lady.  I'll fight them as an engineer."

torek@elf.ee.lbl.gov (Chris Torek) (05/23/91)

In article <1141@mwtech.UUCP> martin@mwtech.UUCP (Martin Weitzel) writes:
>... I'm curious if anybody has ideas from where this misconception
>[about the type of the argument to time()] originated.

Perhaps it dates back to Version 6 Unix, when C did not have a `long'
type.  The time() system call took a pointer to the first of two
`ints'.  In V7 this became a pointer to a long, but of course in V6
pointers and integers were freely interchangeable, and people wrote
such gems as

	struct xxreg {
		int	csr;	/* control/status */
		int	bar;	/* unibus address */
	};

	...
	0177440->bar = bp->b_addr;
	0177440->csr = XXREAD | XXGO;

One can speculate that `long' went in before `pointers are not ints',
and people changed their

	time(vec);

calls to

	t = time(0);

calls, but for backwards compatibility the time() function still
accepted pointers.  It still does; it should be `time_t time(void)',
but compatibility with 20-year-old software is oh so terribly
important :-) .

Perhaps if dmr is indulging his news habit and sees this, he might
comment....
-- 
In-Real-Life: Chris Torek, Lawrence Berkeley Lab CSE/EE (+1 415 486 5427)
Berkeley, CA		Domain:	torek@ee.lbl.gov

jim@sco.COM (Jim Sullivan) (05/23/91)

lothar@tmcsys.UUCP (L. Hirschbiegel) writes:

>In article <1141@mwtech.UUCP> martin@mwtech.UUCP (Martin Weitzel) writes:
>>In article <588@sherpa.UUCP> rac@sherpa.UUCP (Roger Cornelius) writes:
>>[...]
>>>	long seed = time(0L);
>>	                 ^^--------- wrong
>>	           time((long *)0);
>>	                ^^^^^^^^^--- right
>
>If you still don't understand: I'll help you! 
>For this little test program:
>
>main()
>{
>time(0L);
>time((long *)0);
>}
>
>the assembler output from my C compiler is:

	< assembly code illustrating that 0L and (long *)0 both map to 0 >

This if from YOUR C compiler.  And on many systems, similar code would be
produced.  But on many systems 0L and (long *)0 are not equal, so writers
of portable code should do the right thing and not assume that the entire
work is the same as their machine.

>
>Repeat after me: IT DOESN'T MATTER :-)

But it does. 

>>I'm always wondering why people can't grasp
>>the difference between a plain integer, a long and pointers to any of it.

Here! Here!


>>Martin Weitzel, email: martin@mwtech.UUCP, voice: 49-(0)6151-6 56 83
>Lothar Hirschbiegel

-- 
Jim Sullivan				"Revenue Canada:
SCO Canada, Inc.			 	You Make It
Toronto, Ontario, Canada		 	We Take It"
jim@scocan.com, ...!uunet!scocan!jim	- Backbench comic in the Globe

sef@kithrup.COM (Sean Eric Fagan) (05/23/91)

In article <1141@mwtech.UUCP> martin@mwtech.UUCP (Martin Weitzel) writes:
>In article <588@sherpa.UUCP> rac@sherpa.UUCP (Roger Cornelius) writes:
>>	long seed = time(0L);
>	                 ^^--------- wrong
>	           time((long *)0);
>	                ^^^^^^^^^--- right
>Note that the argument to the time system call is a `long *', aka
>pointer to long. Repeat after me: POINTER to long.

On the other hand, if you have an ansi-conformant compiler, and a prototype
is in scope, then either solution will work properly.

-- 
Sean Eric Fagan  | "I made the universe, but please don't blame me for it;
sef@kithrup.COM  |  I had a bellyache at the time."
-----------------+           -- The Turtle (Stephen King, _It_)
Any opinions expressed are my own, and generally unpopular with others.

cpcahil@virtech.uucp (Conor P. Cahill) (05/23/91)

lothar@tmcsys.UUCP (L. Hirschbiegel) writes:

>Ever tried to RTFM for yourself? 
>If you still don't understand: I'll help you! 
>For this little test program:
>main()
>{
>time(0L);
>time((long *)0);
>}
>the assembler output from my C compiler is [the same for both.]
>Repeat after me: IT DOESN'T MATTER :-)

Boy, you just showed the world that you are a junior programmer who 
hasn't yet realized that just because something works on your system
doesn't mean it is right.  

The code you show won't work reliably on systems where the size of
a pointer is different from the size of an integer (for ex: large 
model programs on an 8086 or 80286). 

Before you jump on someone elses case, be sure you know what
you are talking about.
-- 
Conor P. Cahill            (703)430-9247        Virtual Technologies, Inc.
uunet!virtech!cpcahil                           46030 Manekin Plaza, Suite 160
                                                Sterling, VA 22170 

toy@pegasus.crd.ge.com (Raymond L. Toy) (05/23/91)

In article <4138@uc.msc.umn.edu> you write:
|> In article <1141@mwtech.UUCP> martin@mwtech.UUCP (Martin Weitzel) writes:
|> >In article <588@sherpa.UUCP> rac@sherpa.UUCP (Roger Cornelius) writes:
|>[...]
|> 
|> You are right -- to ensure portability, you should always pass what
is expected
|> (i.e. a pointer and not a long).  This way, if someday a machine is created 
|> on which a pointer to a long is a different size then a long, the
program will
|> still work.  However, I don't know of any machines on which the two differ.

Such machines do exist and are very common.  In particular, a PC has
this property when using the small memory model: a pointer is 16 bits
long, but a long is 32 bits.

Also, at school, we had a Harris H800 mini, a 24-bit machine.  A
pointer was 24 bits long (really only 22!!!), and a long was really 47
bits long!!!!  This was a rather bizarre machine, to say the least.
It's dead and gone now, fortunately.

Ray
ray ----> toy@soho.crd.ge.com

|> 
|> -Jeff
|> ---
|> Jeff Turner                           EMAIL: jeff@msc.edu
|> Minnesota Supercomputer Center, Inc.  VOICE: (612) 626-0544
|> Minneapolis, Minnesota  55415           FAX: (612) 624-6550

scotte@applix.com (Scott Evernden) (05/23/91)

Someone, please, anyone- 
Name for me any modern computer in any kind of common use which will
barf at:

	time(0L);

-scott

barmar@think.com (Barry Margolin) (05/23/91)

In article <1200@applix.com> scotte@applix.UUCP (Scott Evernden) writes:
>Name for me any modern computer in any kind of common use which will
>barf at:
>	time(0L);

I frequently respond to this frequent question with one or two machines I'm
familiar with, but I'm not going to do that this time.  Suffice it to say
that there *are* systems where the null pointer is not implemented as the
same bit pattern as 0L.

No, these systems are not "in common use".  90% of all C programs are
probably running on 80*86, 680x0, VAX, and SPARC processors, but does that
mean that all other systems should be ignored?

Prototypes are the most appropriate solution to this problem.  With a
prototype in scope, the above call works right on any ANSI-conforming
implementation.  But if you need to be portable to pre-ANSI
implementations, then is "(char *)0" so hard to write?  Not only does it
inform the compiler of the correct code to generate (in implementations
that care), but it also makes the intent clearer to *human* readers of the
code.  What's the point of looking for a way around something that's so
clearly right?
-- 
Barry Margolin, Thinking Machines Corp.

barmar@think.com
{uunet,harvard}!think!barmar

boyd@prl.dec.com (Boyd Roberts) (05/23/91)

In article <13455@dog.ee.lbl.gov>, torek@elf.ee.lbl.gov (Chris Torek) writes:
> 
> Perhaps it dates back to Version 6 Unix, ...

I think Chris is right.  If you look at any routine that requires a long
(in the `standard' C library) it'll be passed by a pointer.

One Computing Centre once changed ctime(3) to take a long instead of a long *.
Boy, were they sorry.  Broken code from here to backups...


Boyd Roberts			boyd@prl.dec.com

``When the going gets wierd, the weird turn pro...''

conor@lion.inmos.co.uk (Conor O'Neill) (05/23/91)

In article <4138@uc.msc.umn.edu> jeff@uf.UUCP (Jeff Turner) writes:
>You are right -- to ensure portability, you should always pass what is expected
>(i.e. a pointer and not a long).  This way, if someday a machine is created 
>on which a pointer to a long is a different size then a long, the program will
>still work.  However, I don't know of any machines on which the two differ.

Think of a 16-bit machine, where pointers are 16-bits, but longs are 32-bits.
Not a particularly obscure possibility.

(Oh - by the way - we sell one - the IMS T222 transputer).

---
Conor O'Neill, Software Group, INMOS Ltd., UK.
UK: conor@inmos.co.uk		US: conor@inmos.com
"It's state-of-the-art" "But it doesn't work!" "That is the state-of-the-art".

imc@prg.ox.ac.uk (Ian Collier) (05/23/91)

In article <381@tmcsys.UUCP>, lh@aega84.UUCP (L. Hirschbiegel) wrote:
[about the argument of time()]
>	  NAME
>	       time - get time
>
>	  DESCRIPTION
>	       The time	system call returns the	value of time in seconds
>	       since 00:00:00 Greenwich	Mean Time (GMT), January 1, 1970.
>
>	       If tloc is non-zero, the	return value is	also stored in the
>                   ^^^^^^^^^^^
>	       location	to which tloc points.

Obviously the writers of your manual don't know the difference between a
long and a pointer, then. Ours seems to have it about right...

SYNOPSIS
...
     time_t time(tloc)
     time_t *tloc;

DESCRIPTION
     time() returns the time since 00:00:00 GMT,  Jan.  1,  1970,
     measured in seconds.

     If tloc is non-NULL, the return value is also stored in  the
                    ^^^^
     location to which tloc points.

>For this little test program:
...
>the assembler output from my C compiler is:
...

All that means is that your computer represents a NULL pointer by zero
(also evident from your manual page). So for time(0L) it pushes a long
zero, and for time((long *)0) it pushes a null pointer, which is just
a long zero. That will happen on most computers, but not all. (As
someone has pointed out, however, if a prototype for time() is in scope
then a zero will be converted into a null pointer, probably without a
warning message).

Ian Collier
Ian.Collier@prg.ox.ac.uk | imc@ecs.ox.ac.uk

pt@geovision.gvc.com (Paul Tomblin) (05/23/91)

scotte@applix.com (Scott Evernden) writes:

>Someone, please, anyone- 
>Name for me any modern computer in any kind of common use which will
>barf at:

>	time(0L);

Well, when I worked on a MVS/XA system, it probably would have barfed on that
line, but only because we didn't have a C compiler on it.....
:-)


//GO.SYSIN DD *, DO-DAH, DO-DAH
-- 
Paul Tomblin, Department of Redundancy Department.       ! My employer does 
Two roads diverged in a wood, and I/ I took the one less ! not stand by my
travelled by/ And that is why I'm lost, dammit...        ! opinions.... 
pt@geovision.gvc.com or {cognos,uunet}!geovision!pt      ! Me neither.

6sigma2@polari.UUCP (Brian Matthews) (05/23/91)

In article <381@tmcsys.UUCP> lh@aega84.UUCP (L. Hirschbiegel) writes:
|In article <1141@mwtech.UUCP> martin@mwtech.UUCP (Martin Weitzel) writes:
|>In article <588@sherpa.UUCP> rac@sherpa.UUCP (Roger Cornelius) writes:
|>[...]
|>>	long seed = time(0L);
|>	                 ^^--------- wrong
|>	           time((long *)0);
|>	                ^^^^^^^^^--- right
|Ever tried to RTFM for yourself? 
|
|	  NAME
|	       time - get time
|	       If tloc is non-zero, the	return value is	also stored in the
|                   ^^^^^^^^^^^
|	       location	to which tloc points.

You'll get yourself in trouble by taking parts of TFM out of context.
The part you left out reads something like:

	long time ((long *) 0)
	long time (tloc)
	long *tloc;

Tloc still has to be of the correct type, whether zero or non-zero.  This
can happen by having a prototype in scope or with an appropriate cast.

|If you still don't understand: I'll help you! 
|For this little test program:
|[program calling time with (incorrect) 0L and (correct) (long *)0]

This just proves that on your particular OS at some particular release
level and version with some particular version of gcc, it happens to
work.  In general, portable code must assume time(0L) won't work.

|Repeat after me: IT DOESN'T MATTER :-)

Please remind me never to use any code you've written.  It will
undoubtedly fail in many strange and mysterious (to you at least) ways.

jim@segue.segue.com (Jim Balter) (05/24/91)

In article <4138@uc.msc.umn.edu> jeff@uf.UUCP (Jeff Turner) writes:
>Of course by definition, passing (long*)0 is the only truely correct
>way to pass a long pointer that points to address 0, but that is toooooooo
>much to type :-)

By the ANSI standard, if there is a prototype in scope, a zero value of any
type is "correct".  Without a prototype, only (time_t *)0 is correct.

lothar@tmcsys.UUCP (L. Hirschbiegel) (05/24/91)

In article <1991May22.190908.5311@virtech.uucp> cpcahil@virtech.uucp (Conor P. Cahill) writes:
>
>The code you show won't work reliably on systems where the size of
>a pointer is different from the size of an integer (for ex: large 
>model programs on an 8086 or 80286). 

This was posted to newsgroup "comp.UNIX.SYSV386", right??
This was NOT posted to newsgroup "comp.unix.any_intel_product", right??
The original poster had problems with SCO-UNIX password generator, not
with a password generator running under MS-C6.0 in tiny-mode, right??

Martin was referring to a "time" syscall argument mismatch under SCO-UNIX.
I pointed out, that it really makes no difference for the argument value itself.
I did NOT say this is a general rule-of-thumb for all kinds of cpus
and all kinds of compilers?!?!

>Before you jump on someone elses case, be sure you know what
>you are talking about.

Before you answer in a newsgroup make sure you realise what that newsgroup
is about.

>Conor P. Cahill            (703)430-9247        Virtual Technologies, Inc.

-- 
-----------------------------------------------
L. Hirschbiegel, AEG - A84, Frankfurt (Germany) 
email: unido!aega84!lh     tel: -49-69-66414316  
-----------------------------------------------

jim@segue.segue.com (Jim Balter) (05/24/91)

In article <1991May22.130713.25852@sco.COM> david@sco.COM (David Fiander) writes:
>There exist architectures on which the NULL pointer is different from
>"all bits 0".

This isn't relevant if using ANSI prototypes, since any form of zero is
implicitly converted to the appropriate null pointer, no matter how it is
represented.  If you aren't using ANSI prototypes, then you should manually
cast everything into the proper type, and run lint religiously.  Hopefully,
some day, we will only concerned with the first case.

>In fact, if you can get the compiler people to agree to
>it, the best value for the NULL pointer is something that is an invalid
>virtual memory address, because then, when somebody tries to dereference
>it, you get a core dump (note that 0 might be a valid address which would
>never be referred to by the user, for example: the address of the C
>startup code).

This doesn't require a non-zero representation of NULL, since page 0 of
the virtual address space can usually be made inaccessible.  Most UNIX systems
don't do it because there are too many bad UNIX programs written by too many
bad UNIX programmers, and any desire to do the "right" thing is overridden
by the market demand to allow programs that dereference NULL to continue to
"work".

cpcahil@virtech.uucp (Conor P. Cahill) (05/24/91)

lothar@tmcsys.UUCP (L. Hirschbiegel) writes:

>This was posted to newsgroup "comp.UNIX.SYSV386", right??

NO.  It was cross-posted to comp.unix.sysv386 AND comp.lang.c

>Martin was referring to a "time" syscall argument mismatch under SCO-UNIX.

Martin was saying that it was incorrect useage to call time(0L) period.

>I pointed out, that it really makes no difference for the argument value itself.
>I did NOT say this is a general rule-of-thumb for all kinds of cpus
>and all kinds of compilers?!?!

You did not say "it makes on difference under SCO UNIX".   You said it makes
no difference.  Either way (on SCO UNIX or not) it is incorrect to code 
time(0L) as opposed to time((long*)0).

>Before you answer in a newsgroup make sure you realise what that newsgroup
>is about.

Learn how to read headers.

-- 
Conor P. Cahill            (703)430-9247        Virtual Technologies, Inc.
uunet!virtech!cpcahil                           46030 Manekin Plaza, Suite 160
                                                Sterling, VA 22170 

jja@wsl.ie (John Allen on wsl) (05/24/91)

In article <1200@applix.com> scotte@applix.UUCP (Scott Evernden) writes:
>Someone, please, anyone- 
>Name for me any modern computer in any kind of common use which will
>barf at:
>
>	time(0L);
>
>-scott

I suppose this is a good a reason as you can come up with to do it 
inorrectly.

You belong to the old school of 'we used to do it wrong, we still do it wrong'

lbr@holos0.uucp (Len Reed) (05/24/91)

In article <383@tmcsys.UUCP> lothar@tmcsys.UUCP (L. Hirschbiegel) writes:

>This was posted to newsgroup "comp.UNIX.SYSV386", right??

>Martin was referring to a "time" syscall argument mismatch under SCO-UNIX.
>I did NOT say this is a general rule-of-thumb for all kinds of cpus
>and all kinds of compilers?!?!

Well, you really should have said "Though it's poor programming practice,
it makes no difference on the 30386."  If your point was that such-and-such
couldn't be the source of certain anamolous behavior, you could have been
clearer.  If your point was that this was acceptable coding practice,
I strongly disagree.

Good programmers distinguish between things that work because they're
done correctly and things that work in spite of being done incorrectly.
Knowlingly to exploit such things as
	sizeof(int) == sizeof(long)  == sizeof(long *)
with the smug idea that the code will never run on any other machine
is shortsighted.
-- 
Len Reed
Holos Software, Inc.
Voice: (404) 496-1358
UUCP: ...!gatech!holos0!lbr

lbr@holos0.uucp (Len Reed) (05/24/91)

In article <1991May22.130713.25852@sco.COM> david@sco.COM (David Fiander) writes:
>There exist architectures on which the NULL pointer is different from
>"all bits 0".  In fact, if you can get the compiler people to agree to
>it, the best value for the NULL pointer is something that is an invalid
>virtual memory address, because then, when somebody tries to dereference
>it, you get a core dump (note that 0 might be a valid address which would
>never be referred to by the user, for example: the address of the C
>startup code).

Under what architecture is a NULL pointer not "all bits 0"?  The problems,
as many have said, result when a pointer has fewer or more bits than
an integer (or a long).  NULL pointers *are* all zeros, though, since
casting zero to a pointer must yield a null pointer.  (Maybe there's
a loophole here in ANSI that says that (void *)0 is a null pointer but
the compiler could implement that casted zero as somthing other than
a pattern of zeros.  Not likely in the real world.)

You're certainly right that a NULL that produced a virtual memory fault
upon any use would be better than a virtual zero address.  But it's not
the "compiler people" who would have to agree to this.  Far too much
existing code would be broken by a move to this, I'm afraid.
-- 
Len Reed
Holos Software, Inc.
Voice: (404) 496-1358
UUCP: ...!gatech!holos0!lbr

lothar@tmcsys.UUCP (L. Hirschbiegel) (05/25/91)

>This just proves that on your particular OS at some particular release
>level and version with some particular version of gcc, it happens to
>work.  In general, portable code must assume time(0L) won't work.

To come to an end with this really annoying 'discussion' please accept
the following statement:
the whole thread of time(0L) vs. time((long *)0) was about
the **Intel i386 processor** running under **ISC/SCO-UNIX** (Martin 
Weitzel's posting as a reply and my own followup).
I didn't intend to crosspost this to com.lang.c but it happened somehow.
This admittedly gave it a different kind of taste... 
I did not even realize this was also in comp.lang.c (thanks, steve, for the
warning!).
Since I had included assembler output for the i386 and also a part of
the SysV/386 man page for 'time' I thought it would be clear what I was talking
about. It was also obvious from the subject line about SCO-UNIX.
It was most interesting to see, how some people declared my included
assembler listing as "irrelevant", thus pushing the topic to a level
of abstraction it was never ment to be. It was EXACTLY for i386 assembler
on a box running UNIX, nothing else.
If you can't find a reason to flame - just create one...
Now everybody is telling me this will not run on an 8086, i286 or some kind
of superprocessor with 124 bit pointers and 12 bit longs. Thanks for the help!
One guy (forgot the name, but he must have been recently out of school, 'cause
he still was arguing with me about his math teacher) even proved it doesn't
work on a PDP11. 
Quite irritating, since nobody claimed it would run on a PDP11.
Nice proof, anyway. My own proof was (only!) for the i386 under ISC-UNIX - 
my fault that I didn't state it loud n'clear enough in my original posting.

One can of course argue about what people think is "good programming
practice", but that's different from saying "you don't know what you are
talking about" or "you fool think your unix box is the center of the
world". At least in my opinion.

So, *please stop* sending me any more hate mail. I'm already enlighted as
a "junior programmer" (this was one of the more modest things I received
by mail; some nice guys hanging around here).

-- 
-----------------------------------------------
L. Hirschbiegel, AEG - A84, Frankfurt (Germany) 
email: unido!aega84!lh     tel: -49-69-66414316  
-----------------------------------------------

gwyn@smoke.brl.mil (Doug Gwyn) (05/25/91)

In article <384@tmcsys.UUCP> lothar@tmcsys.UUCP (L. Hirschbiegel) writes:
>At least in my opinion.

But the original question clearly indicated an understanding that this
was a portability issue, and it was YOU who decided to turn it into a
386-specific issue and claim that the difference between correct
portable practice and 386-dependent coding "doesn't matter".  It did
matter to the original purpose of the question.  It should also matter
even if you are at the moment programming with the expectation that
the program will run only on a 386, because there is no guarantee that
the non-portable practice will continue to "work" even using future
releases of the "same" C compiler on the "same" hardware platform.
Thus, it would be much wiser to code this properly in the first place,
especially given that it is easy to do so.

In MY opinion, you deserved to be flamed, on several counts.

sef@kithrup.COM (Sean Eric Fagan) (05/25/91)

In article <1991May24.151350.22705@holos0.uucp> lbr@holos0.uucp (Len Reed) writes:
>Under what architecture is a NULL pointer not "all bits 0"?  

Pr1me, Cyber 180, and another weird machine whose name I forget but might
have been a Burroughs (excuse me, Unisys) machine.

>NULL pointers *are* all zeros, though, since
>casting zero to a pointer must yield a null pointer.  

That is a non-sequitor.  Casting a constant 0 to a pointer must yeild a null
pointer.  Casting an integer, whose value is 0, to a pointer does not
necessarily yield a null pointer.

>(Maybe there's
>a loophole here in ANSI that says that (void *)0 is a null pointer but
>the compiler could implement that casted zero as somthing other than
>a pattern of zeros.  Not likely in the real world.)

ANSI says exactly that.  You should *never* assume that that things are
otherwise.  Talk to Henry, Doug, or Chris about such things; I'll just get
into an argument and end up calling you a fool or worse.  (HGoC might
*think* so, but I don't think they'll *say* so.  Well, actually, I'm not so
sure about that, now that I think about it.)

>You're certainly right that a NULL that produced a virtual memory fault
>upon any use would be better than a virtual zero address.  But it's not
>the "compiler people" who would have to agree to this.  Far too much
>existing code would be broken by a move to this, I'm afraid.

Many, many people have made address 0 result in an address fault (who said
*anything* about virtual memory?  lots of machines don't have virtual
memory, and some of them still manage to compile C).  Some people have made
it work, simply to placate stupid programmer, such as you appear to be.
Frankly, I would *much* rther have my OS complain, so I can track down the
error (for that's what it is) during development.  (SCO, for example, has
address 0 readable and writable, because too many applications people
bitched about it.  I prefer having a core dump, myself.)

-- 
Sean Eric Fagan  | "I made the universe, but please don't blame me for it;
sef@kithrup.COM  |  I had a bellyache at the time."
-----------------+           -- The Turtle (Stephen King, _It_)
Any opinions expressed are my own, and generally unpopular with others.

scs@adam.mit.edu (Steve Summit) (05/25/91)

In article <1991May24.151350.22705@holos0.uucp> lbr@holos0.uucp (Len Reed) writes:
>Under what architecture is a NULL pointer not "all bits 0"?

Would it be at all possible for anyone who feels the urge to
contribute to this thread to read the comp.lang.c frequently-
asked questions list first, before posting anything more?  (If
you just joined us, this is a *very* old topic, at least for
comp.lang.c, and nothing new is being said.  If comp.unix.sysv386
finds this fascinating, please remove comp.lang.c from the
Newsgroups: line.)

                                            Steve Summit
                                            scs@adam.mit.edu

scs@adam.mit.edu (Steve Summit) (05/25/91)

In article <1991May24.151350.22705@holos0.uucp> lbr@holos0.uucp (Len Reed) writes:
>Under what architecture is a NULL pointer not "all bits 0"?
>...
>(Maybe there's
>a loophole here in ANSI that says that (void *)0 is a null pointer but
>the compiler could implement that casted zero as somthing other than
>a pattern of zeros.  Not likely in the real world.)

It's not at all unlikely.

For those of you who have no access to or interest in comp.lang.c,
here are two relevant answers from its frequently-asked questions list:

13.  Given all the confusion surrounding null pointers, wouldn't it be
     easier simply to require them to be represented internally by
     zeroes?

A:   If for no other reason, doing so would be ill-advised because it
     would unnecessarily constrain implementations which would otherwise
     naturally represent null pointers by special, nonzero bit patterns,
     particularly when those values would trigger automatic hardware
     traps for invalid accesses.

     Besides, what would this requirement really accomplish?  Proper
     understanding of null pointers does not require knowledge of the
     internal representation, whether zero or nonzero.  Assuming that
     null pointers are internally zero does not make any code easier to
     write (except for a certain ill-advised usage of calloc; see
     question 52).  Known-zero internal pointers would not obviate casts
     in function calls, because the _size_ of the pointer might still be
     different from that of an int.

14.  Seriously, have any actual machines really used nonzero null
     pointers?

A:    "Certain Prime computers use a value different from all-
      bits-0 to encode the null pointer.  Also, some large
      Honeywell-Bull machines use the bit pattern 06000 to encode
      the null pointer."

                 -- Portable C, by H. Rabinowitz and Chaim Schaap,
                 Prentice-Hall, 1990, page 147.

     The "certain Prime computers" were the segmented 50 series, which
     used segment 07777, offset 0 for the null pointer, at least for
     PL/I.  Later models used segment 0, offset 0 for null pointers in
     C, necessitating new instructions such as TCNP (Test C Null
     Pointer), evidently as a sop to all the extant poorly-written C
     code which made incorrect assumptions.

     The Symbolics Lisp Machine, a tagged architecture, does not even
     have conventional numeric pointers; it uses the pair <NIL, 0>
     (basically a nonexistent <object, offset> handle) as a C null
     pointer.

                                            Steve Summit
                                            scs@adam.mit.edu

Steve.Summit@sunbrk.FidoNet.Org (Steve Summit) (05/25/91)

Reply-To: scs@adam.mit.edu

In article <1991May24.151350.22705@holos0.uucp> lbr@holos0.uucp (Len Reed) writes:
>Under what architecture is a NULL pointer not "all bits 0"?

Would it be at all possible for anyone who feels the urge to
contribute to this thread to read the comp.lang.c frequently-
asked questions list first, before posting anything more?  (If
you just joined us, this is a *very* old topic, at least for
comp.lang.c, and nothing new is being said.  If comp.unix.sysv386
finds this fascinating, please remove comp.lang.c from the

                                            Steve Summit
                                            scs@adam.mit.edu

 * Origin: Seaeast - Fidonet<->Usenet Gateway - sunbrk (1:343/15.0)

Steve.Summit@sunbrk.FidoNet.Org (Steve Summit) (05/25/91)

Reply-To: scs@adam.mit.edu

In article <1991May24.151350.22705@holos0.uucp> lbr@holos0.uucp (Len Reed) writes:
>Under what architecture is a NULL pointer not "all bits 0"?
>...
>(Maybe there's
>a loophole here in ANSI that says that (void *)0 is a null pointer but
>the compiler could implement that casted zero as somthing other than
>a pattern of zeros.  Not likely in the real world.)

It's not at all unlikely.

For those of you who have no access to or interest in comp.lang.c,
here are two relevant answers from its frequently-asked questions list:

13.  Given all the confusion surrounding null pointers, wouldn't it be
     easier simply to require them to be represented internally by
     zeroes?

A:   If for no other reason, doing so would be ill-advised because it
     would unnecessarily constrain implementations which would otherwise
     naturally represent null pointers by special, nonzero bit patterns,
     particularly when those values would trigger automatic hardware
     traps for invalid accesses.

     Besides, what would this requirement really accomplish?  Proper
     understanding of null pointers does not require knowledge of the
     internal representation, whether zero or nonzero.  Assuming that
     null pointers are internally zero does not make any code easier to
     write (except for a certain ill-advised usage of calloc; see
     question 52).  Known-zero internal pointers would not obviate casts
     in function calls, because the _size_ of the pointer might still be
     different from that of an int.

14.  Seriously, have any actual machines really used nonzero null
     pointers?

A:    "Certain Prime computers use a value different from all-
      bits-0 to encode the null pointer.  Also, some large
      Honeywell-Bull machines use the bit pattern 06000 to encode
      the null pointer."

                 -- Portable C, by H. Rabinowitz and Chaim Schaap,
                 Prentice-Hall, 1990, page 147.

     The "certain Prime computers" were the segmented 50 series, which
     used segment 07777, offset 0 for the null pointer, at least for
     PL/I.  Later models used segment 0, offset 0 for null pointers in
     C, necessitating new instructions such as TCNP (Test C Null
     Pointer), evidently as a sop to all the extant poorly-written C
     code which made incorrect assumptions.

     The Symbolics Lisp Machine, a tagged architecture, does not even
     have conventional numeric pointers; it uses the pair <NIL, 0>
     (basically a nonexistent <object, offset> handle) as a C null
     pointer.

                                            Steve Summit
                                            scs@adam.mit.edu

 * Origin: Seaeast - Fidonet<->Usenet Gateway - sunbrk (1:343/15.0)

mouse@thunder.mcrcim.mcgill.edu (der Mouse) (05/25/91)

In article <383@tmcsys.UUCP>, lothar@tmcsys.UUCP (L. Hirschbiegel) writes:
> In article <1991May22.190908.5311@virtech.uucp> cpcahil@virtech.uucp (Conor P. Cahill) writes:
>> The code you show won't work reliably on systems where the size of a
>> pointer is different from the size of an integer (for ex: large
>> model programs on an 8086 or 80286).

> This was posted to newsgroup "comp.UNIX.SYSV386", right??

It was *also* posted to comp.lang.c.

> Martin was referring to a "time" syscall argument mismatch under
> SCO-UNIX.  I pointed out, that it really makes no difference for the
> argument value itself.  I did NOT say this is a general rule-of-thumb
> for all kinds of cpus and all kinds of compilers?!?!

Then you should have removed comp.lang.c from the Newsgroups: line
before posting.

					der Mouse

			old: mcgill-vision!mouse
			new: mouse@larry.mcrcim.mcgill.edu

der.Mouse@sunbrk.FidoNet.Org (der Mouse) (05/26/91)

In article <383@tmcsys.UUCP>, lothar@tmcsys.UUCP (L. Hirschbiegel) writes:
> In article <1991May22.190908.5311@virtech.uucp> cpcahil@virtech.uucp (Conor P. Cahill) writes:
>> The code you show won't work reliably on systems where the size of a
>> pointer is different from the size of an integer (for ex: large
>> model programs on an 8086 or 80286).

> This was posted to newsgroup "comp.UNIX.SYSV386", right??

It was *also* posted to comp.lang.c.

> Martin was referring to a "time" syscall argument mismatch under
> SCO-UNIX.  I pointed out, that it really makes no difference for the
> argument value itself.  I did NOT say this is a general rule-of-thumb
> for all kinds of cpus and all kinds of compilers?!?!

Then you should have removed comp.lang.c from the Newsgroups: line
before posting.

					der Mouse

			old: mcgill-vision!mouse
			new: mouse@larry.mcrcim.mcgill.edu

 * Origin: Seaeast - Fidonet<->Usenet Gateway - sunbrk (1:343/15.0)

allbery@NCoast.ORG (Brandon S. Allbery KF8NH) (05/26/91)

As quoted from <1991May25.002706.27552@kithrup.COM> by sef@kithrup.COM (Sean Eric Fagan):
+---------------
| Many, many people have made address 0 result in an address fault (who said
| *anything* about virtual memory?  lots of machines don't have virtual
| memory, and some of them still manage to compile C).  Some people have made
| it work, simply to placate stupid programmer, such as you appear to be.
| Frankly, I would *much* rther have my OS complain, so I can track down the
| error (for that's what it is) during development.  (SCO, for example, has
| address 0 readable and writable, because too many applications people
| bitched about it.  I prefer having a core dump, myself.)
+---------------

Whatever happened to (System V) ld using a default ld script in /lib?  Plexus
System V did this, and it was trivial to change it from the default to not
mapping page 0 (they even provided a script for this, and a special ld option
that used that script instead; but changing the default script worked fine).

++Brandon
-- 
Me: Brandon S. Allbery			 KF8NH: DC to LIGHT!  [44.70.4.88]
Internet: allbery@NCoast.ORG		 Delphi: ALLBERY
uunet!usenet.ins.cwru.edu!ncoast!allbery

rac@sherpa.UUCP (Roger Cornelius) (05/26/91)

From article <1991May24.044751.5933@virtech.uucp>, by cpcahil@virtech.uucp (Conor P. Cahill):
> lothar@tmcsys.UUCP (L. Hirschbiegel) writes:
> 
>>This was posted to newsgroup "comp.UNIX.SYSV386", right??
> 
> NO.  It was cross-posted to comp.unix.sysv386 AND comp.lang.c

No, the original article, as well as my followup (I posted the code
everyone has been arguing about) were posted only to comp.unix.sysv386.
Some later follow-upper must have done the cross-posting.  Here are
the headers from my post:

Subject: Re: SCO password generator
Newsgroups: comp.unix.sysv386
References: <1991May14.040042.15199@jpradley.jpr.com>

Regardless, of where it was posted, I think everybody now knows that
time(0L) != time((long*)0).  I'm sure I do.  For those interested,
I've included a patch below :-).  Hopefully this will end this thread.

Roger

--- cut here ---

*** a1.c	Sat May 25 16:29:31 1991
--- a2.c	Sat May 25 16:29:58 1991
***************
*** 11,17 ****
  {
  	char word[MAX], hyword[2*MAX];
! 	long seed = time(0L);
  
  	set_auth_parameters(ac,av);
--- 11,17 ----
  {
  	char word[MAX], hyword[2*MAX];
! 	long seed = time((long*)0);
  
  	set_auth_parameters(ac,av);
--- cut here ---

--
Roger Cornelius          rac@sherpa.UUCP         uunet!sherpa!rac

henry@zoo.toronto.edu (Henry Spencer) (05/26/91)

In article <1991May25.002706.27552@kithrup.COM> sef@kithrup.COM (Sean Eric Fagan) writes:
>...Talk to Henry, Doug, or Chris about such things; I'll just get
>into an argument and end up calling you a fool or worse.  (HGoC might
>*think* so, but I don't think they'll *say* so.  Well, actually, I'm not so
>sure about that, now that I think about it.)

Chris is an extremely nice and amazingly patient guy and doesn't say such
things.  Doug and I have our limits. :-)

Actually, the people Len really wants to talk to are the IBM AS/400 people,
whose machine is an exception to almost every naive misconception about C
you have ever seen.  Rumor hath it that if you think "ANSI C *surely* could
have promised XYZ instead of the watered-down version they actually gave us",
there is a high probability that the AS/400 was a major counterexample.
-- 
"We're thinking about upgrading from    | Henry Spencer @ U of Toronto Zoology
SunOS 4.1.1 to SunOS 3.5."              |  henry@zoo.toronto.edu  utzoo!henry

david@sco.COM (David Fiander) (05/27/91)

In article <1991May24.151350.22705@holos0.uucp> lbr@holos0.uucp (Len Reed) writes:
>
>You're certainly right that a NULL that produced a virtual memory fault
>upon any use would be better than a virtual zero address.  But it's not
>the "compiler people" who would have to agree to this.  Far too much
>existing code would be broken by a move to this, I'm afraid.

No, all I have to do is convince the compiler people.  They don't
particularly care if somebody else's broken code breaks; just ask anybody
that has worked on an optimizer.  Most of the bugs reported against
HCR-PCO (the Portable Code Optimizer) turned out to be bugs in the
application source which worked until an agressive optimizer hacked the
code into something else.

David.Fiander@sunbrk.FidoNet.Org (David Fiander) (05/28/91)

In article <1991May24.151350.22705@holos0.uucp> lbr@holos0.uucp (Len Reed) writes:
>
>You're certainly right that a NULL that produced a virtual memory fault
>upon any use would be better than a virtual zero address.  But it's not
>the "compiler people" who would have to agree to this.  Far too much
>existing code would be broken by a move to this, I'm afraid.

No, all I have to do is convince the compiler people.  They don't
particularly care if somebody else's broken code breaks; just ask anybody
that has worked on an optimizer.  Most of the bugs reported against
HCR-PCO (the Portable Code Optimizer) turned out to be bugs in the
application source which worked until an agressive optimizer hacked the
code into something else.

 * Origin: Seaeast - Fidonet<->Usenet Gateway - sunbrk (1:343/15.0)

chap@art-sy.detroit.mi.us (j chapman flack) (06/01/91)

In article <1991May23.040054.23555@Think.COM> barmar@think.com writes:
>No, these systems are not "in common use".  90% of all C programs are
>probably running on 80*86, 680x0, VAX, and SPARC processors, but does that

Mr. Margolin implies that time(0L) is not a problem on the 80*86.

For x > 2, the 80x86 supports two flavors of pointer (near and far) and two
sizes of offset (16 and 32 bit).  The combinations are:

  near, 16:          sizeof(*long) != sizeof(long)
  far,  16:          sizeof(*long) == sizeof(long) BUT null value not all-zero
                                                   in the implementations I
                                                   know of
  far,  32:          sizeof(*long) != sizeof(long)
  near, 32:          sizeof(*long) == sizeof(long) and null value COULD be
                                                   all-zero if the compiler
                                                   implementor felt like it.

So time(0L) *is* incorrect in (at least) 3 out of 4 cases on an 80x86, x > 2.
It's incorrect in *all* cases on earlier 80x86's (though I could imagine an
implementation that used 0x0000:0x0000 as the null pointer; the ones I know
of all use segment:0x0000.)

Of course all my sizeof() comparisons above are based on a 32-bit long, which
is yet another assumption....

I replied to Mr. Evernden by mail before I saw this article.  Sorry for the
duplication.
-- 
Chap Flack                         Their tanks will rust.  Our songs will last.
chap@art-sy.detroit.mi.us                                    -MIKHS 0EODWPAKHS

Nothing I say represents Appropriate Roles for Technology unless I say it does.

andre@targon.UUCP (Andre van Dalen) (06/02/91)

In article <381@tmcsys.UUCP> lh@aega84.UUCP (L. Hirschbiegel) writes:
  >In article <1141@mwtech.UUCP> martin@mwtech.UUCP (Martin Weitzel) writes:
  >>In article <588@sherpa.UUCP> rac@sherpa.UUCP (Roger Cornelius) writes:
  >>[...]
  >>>     long seed = time(0L);
  >>                       ^^--------- wrong
  >>                 time((long *)0);
  >>                      ^^^^^^^^^--- right
[ removed assembler listing (gives us a clue :-) ]

  >>Repeat after me: POINTER to long.
  >
  >Repeat after me: IT DOESN'T MATTER :-)

Never worked under MSDOeSn't in different memory models or on 64 bit
machines have you?

-- 
The mail|    AAA         DDDD  It's not the kill, but the thrill of the chase.
demon...|   AA AAvv   vvDD  DD        Ketchup is a vegetable.
hits!.@&|  AAAAAAAvv vvDD  DD                    {nixbur|nixtor}!adalen.via
--more--| AAA   AAAvvvDDDDDD    Andre van Dalen, uunet!hp4nl!targon!andre

sef@kithrup.COM (Sean Eric Fagan) (06/02/91)

In article <9106011048.aa06266@art-sy.detroit.mi.us> chap@art-sy.detroit.mi.us (j chapman flack) writes:
>For x > 2, the 80x86 supports two flavors of pointer (near and far) and two
>sizes of offset (16 and 32 bit).  The combinations are:

Uhm, better go back and reread your manual.  For 808[86] and 80?8[86], there
are two flavours of pointers:  16-bit ("near"), and 32-bit (actually 20 bit
on the '286 and previous), aka "far" in some compilers.

>So time(0L) *is* incorrect in (at least) 3 out of 4 cases on an 80x86, x > 2.

But it won't cause things to fail, except in some very limited cases
(basicly, where one more 16-bit word will cause a stack fault).

>It's incorrect in *all* cases on earlier 80x86's (though I could imagine an
>implementation that used 0x0000:0x0000 as the null pointer; the ones I know
>of all use segment:0x0000.)

Actually, most use segment 0, offset 0, since most people like being able to
use address 0 of an array (yes, the compiler could fudge things, most don't,
though).

>Of course all my sizeof() comparisons above are based on a 32-bit long, which
>is yet another assumption....

long's are guaranteed to be at least 32 bits, as per ANSI C.  Since most
(all?) popular compilers for the iAPX86 architecture (and descendents, of
course) at least claim some measure of ANSI conformance, and 32 bits is
really the only feasible size of a long (other than 16, which defeats the
purpose of a long), you can pretty much rest assured that a long is 32 bits
on an Intel *86 system.

-- 
Sean Eric Fagan  | "I made the universe, but please don't blame me for it;
sef@kithrup.COM  |  I had a bellyache at the time."
-----------------+           -- The Turtle (Stephen King, _It_)
Any opinions expressed are my own, and generally unpopular with others.