memcpy(p,p,len)

2010-04-30 Thread Joakim Tjernlund

Is memcpy supposed to work when the src and dest are the same:
memcpy(p, p, 100);

Jocke



Re: memcpy(p,p,len)

2010-04-30 Thread Jan-Benedict Glaw
On Fri, 2010-04-30 16:08:15 +0200, Joakim Tjernlund 
joakim.tjernl...@transmode.se wrote:
 Is memcpy supposed to work when the src and dest are the same:
 memcpy(p, p, 100);

It may work, but you cannot rely on it. Use memmove() alternatively.

MfG, JBG

-- 
  Jan-Benedict Glaw  jbg...@lug-owl.de  +49-172-7608481
Signature of:  Alles sollte so einfach wie möglich gemacht sein.
the second  :  Aber nicht einfacher.  (Einstein)


signature.asc
Description: Digital signature


Re: memcpy(p,p,len)

2010-04-30 Thread Joakim Tjernlund
Jan-Benedict Glaw jbg...@lug-owl.de wrote on 2010/04/30 16:10:42:

 On Fri, 2010-04-30 16:08:15 +0200, Joakim Tjernlund
 joakim.tjernl...@transmode.se wrote:
  Is memcpy supposed to work when the src and dest are the same:
  memcpy(p, p, 100);

 It may work, but you cannot rely on it. Use memmove() alternatively.

My view too, but gcc 3.4.6 on gcc does this:
struct my_struct {
long a100[100];
};
static inline
func(struct my_struct *h1, struct my_struct *h2)
{
*h1 = *h2;
}
mytest(struct my_struct *my_h1)
{
func(my_h1, my_h1);
}

-
.file   tst.c
.section.text
.align 2
.globl mytest
.type   mytest, @function
mytest:
mflr 0
stwu 1,-16(1)
mr 4,3
li 5,400
stw 0,20(1)
bl memcpy
lwz 0,20(1)
addi 1,1,16
mtlr 0
blr
.size   mytest, .-mytest
.section.note.GNU-stack,,@progbits
.ident  GCC: (GNU) 3.4.6 (Gentoo 3.4.6-r2, ssp-3.4.6-1.0, pie-8.7.9)



Re: memcpy(p,p,len)

2010-04-30 Thread Jan-Benedict Glaw
On Fri, 2010-04-30 16:14:36 +0200, Joakim Tjernlund 
joakim.tjernl...@transmode.se wrote:
 Jan-Benedict Glaw jbg...@lug-owl.de wrote on 2010/04/30 16:10:42:
  On Fri, 2010-04-30 16:08:15 +0200, Joakim Tjernlund
  joakim.tjernl...@transmode.se wrote:
   Is memcpy supposed to work when the src and dest are the same:
   memcpy(p, p, 100);
 
  It may work, but you cannot rely on it. Use memmove() alternatively.
 
 My view too, but gcc 3.4.6 on gcc does this:
[...]

Surely, it may/will work here and there. But it's not portable :)  And
I won't rely on a it worked once fact.

MfG, JBG

-- 
  Jan-Benedict Glaw  jbg...@lug-owl.de  +49-172-7608481
Signature of:  GDB has a 'break' feature; why doesn't it have 'fix' too?
the second  :


signature.asc
Description: Digital signature


Re: memcpy(p,p,len)

2010-04-30 Thread Mark Mielke
Just a quick comment than Jan-Benedict's opinion is widely shared by the 
specification and by the Linux glibc manpage:


DESCRIPTION
   The  memcpy()  function  copies  n bytes from memory area src to 
memory
   area dest.  The memory areas should not overlap.  Use memmove(3) 
if the

   memory areas do overlap.

It doesn't matter if it sometimes works. Sometimes works programs are 
sometimes doesn't work programs. :-)


Cheers,
mark

On 04/30/2010 10:25 AM, Jan-Benedict Glaw wrote:

On Fri, 2010-04-30 16:14:36 +0200, Joakim 
Tjernlundjoakim.tjernl...@transmode.se  wrote:
   

Jan-Benedict Glawjbg...@lug-owl.de  wrote on 2010/04/30 16:10:42:
 

On Fri, 2010-04-30 16:08:15 +0200, Joakim Tjernlund
joakim.tjernl...@transmode.se  wrote:
   

Is memcpy supposed to work when the src and dest are the same:
memcpy(p, p, 100);
 

It may work, but you cannot rely on it. Use memmove() alternatively.
   

My view too, but gcc 3.4.6 on gcc does this:
 

[...]

Surely, it may/will work here and there. But it's not portable :)  And
I won't rely on a it worked once fact.

MfG, JBG

   




RE: memcpy(p,p,len)

2010-04-30 Thread Paul Koning
That would be a bug.

If h1 and h2 were marked __restrict__ then using memcpy to make the
assignment is valid, but without that marking h1 may be == h2 so memmove
is required.

paul

 -Original Message-
 From: Joakim Tjernlund [mailto:joakim.tjernl...@transmode.se]
 Sent: Friday, April 30, 2010 10:15 AM
 To: Jan-Benedict Glaw
 Cc: gcc@gcc.gnu.org
 Subject: Re: memcpy(p,p,len)
 
 Jan-Benedict Glaw jbg...@lug-owl.de wrote on 2010/04/30 16:10:42:
 
  On Fri, 2010-04-30 16:08:15 +0200, Joakim Tjernlund
  joakim.tjernl...@transmode.se wrote:
   Is memcpy supposed to work when the src and dest are the same:
   memcpy(p, p, 100);
 
  It may work, but you cannot rely on it. Use memmove() alternatively.
 
 My view too, but gcc 3.4.6 on gcc does this:
 struct my_struct {
   long a100[100];
 };
 static inline
 func(struct my_struct *h1, struct my_struct *h2)
 {
   *h1 = *h2;
 }
 mytest(struct my_struct *my_h1)
 {
   func(my_h1, my_h1);
 }
 
 -
   .file   tst.c
   .section.text
   .align 2
   .globl mytest
   .type   mytest, @function
 mytest:
   mflr 0
   stwu 1,-16(1)
   mr 4,3
   li 5,400
   stw 0,20(1)
   bl memcpy
   lwz 0,20(1)
   addi 1,1,16
   mtlr 0
   blr
   .size   mytest, .-mytest
   .section.note.GNU-stack,,@progbits
   .ident  GCC: (GNU) 3.4.6 (Gentoo 3.4.6-r2, ssp-3.4.6-1.0,
 pie-8.7.9)



Re: memcpy(p,p,len)

2010-04-30 Thread Joe Buck
On Fri, Apr 30, 2010 at 07:30:33AM -0700, Mark Mielke wrote:
 Just a quick comment than Jan-Benedict's opinion is widely shared by the 
 specification and by the Linux glibc manpage:
 
 DESCRIPTION
 The  memcpy()  function  copies  n bytes from memory area src to 
 memory
 area dest.  The memory areas should not overlap.  Use memmove(3) 
 if the
 memory areas do overlap.
 
 It doesn't matter if it sometimes works. Sometimes works programs are 
 sometimes doesn't work programs. :-)

The typical memcpy function will fail for overlapping but unequal memory
ranges, but will work for src == dst.  Switching to memmove would degrade
performance, and that should only be done if there is an actual, rather
than a theoretical bug.  Note that for this use, it's not possible (if
the program is valid) for the ranges to overlap but be unequal.

Another alternative is that instead of using memcpy, a specialized
function could be used that has the required property (the glibc
memcpy does).


Re: memcpy(p,p,len)

2010-04-30 Thread Richard Guenther
On Fri, Apr 30, 2010 at 5:05 PM, Joe Buck joe.b...@synopsys.com wrote:
 On Fri, Apr 30, 2010 at 07:30:33AM -0700, Mark Mielke wrote:
 Just a quick comment than Jan-Benedict's opinion is widely shared by the
 specification and by the Linux glibc manpage:

 DESCRIPTION
         The  memcpy()  function  copies  n bytes from memory area src to
 memory
         area dest.  The memory areas should not overlap.  Use memmove(3)
 if the
         memory areas do overlap.

 It doesn't matter if it sometimes works. Sometimes works programs are
 sometimes doesn't work programs. :-)

 The typical memcpy function will fail for overlapping but unequal memory
 ranges, but will work for src == dst.  Switching to memmove would degrade
 performance, and that should only be done if there is an actual, rather
 than a theoretical bug.  Note that for this use, it's not possible (if
 the program is valid) for the ranges to overlap but be unequal.

 Another alternative is that instead of using memcpy, a specialized
 function could be used that has the required property (the glibc
 memcpy does).

Note that language semantics come in here as well.  The middle-end
assumes that when an assignment is not BLKmode that the RHS
will be read before the lhs will be written.  It does not assume so
otherwise and the behavior is undefined for overlapping *p and *q
if you do *p = *q.  Thus it is up to the frontend to emit a call to
memmove in this case (the C++ frontend got bitten by this and
was fixed).

Richard.


Re: memcpy(p,p,len)

2010-04-30 Thread Joe Buck
On Fri, Apr 30, 2010 at 08:29:19AM -0700, Richard Guenther wrote:
 On Fri, Apr 30, 2010 at 5:05 PM, Joe Buck joe.b...@synopsys.com wrote:
  On Fri, Apr 30, 2010 at 07:30:33AM -0700, Mark Mielke wrote:
  Just a quick comment than Jan-Benedict's opinion is widely shared by the
  specification and by the Linux glibc manpage:
 
  DESCRIPTION
          The  memcpy()  function  copies  n bytes from memory area src to
  memory
          area dest.  The memory areas should not overlap.  Use memmove(3)
  if the
          memory areas do overlap.
 
  It doesn't matter if it sometimes works. Sometimes works programs are
  sometimes doesn't work programs. :-)
 
  The typical memcpy function will fail for overlapping but unequal memory
  ranges, but will work for src == dst.  Switching to memmove would degrade
  performance, and that should only be done if there is an actual, rather
  than a theoretical bug.  Note that for this use, it's not possible (if
  the program is valid) for the ranges to overlap but be unequal.
 
  Another alternative is that instead of using memcpy, a specialized
  function could be used that has the required property (the glibc
  memcpy does).
 
 Note that language semantics come in here as well.  The middle-end
 assumes that when an assignment is not BLKmode that the RHS
 will be read before the lhs will be written.  It does not assume so
 otherwise and the behavior is undefined for overlapping *p and *q
 if you do *p = *q.  Thus it is up to the frontend to emit a call to
 memmove in this case (the C++ frontend got bitten by this and
 was fixed).

If the only possibilities are that p == q, or *p and *q do not overlap,
then
  if (p != q)
 memcpy(p, q, n);
would be cheaper than memmove, which has to choose between forward and
backward copying to handle overlap.  However, some memcpy implementations
(including the one in glibc) will do the right thing even without the
test.

If structure copying suddenly produces memmove calls, that would not
be good.