git/list[1] front-page[2] threads[3] people[4] search[5] about
 

Re: [PATCH v1] Travis: also test on 32-bit Linux

From
René Scharfe <l.s.r@web.de>
Date
Mar 11, 2017, 14:17 UTC
Message-ID
<b0d41423-7227-3417-b4b1-fcf47a66f64b@web.de>
In-Reply-To
<xmqqr324wvum.fsf@gitster.mtv.corp.google.com>
Am 11.03.2017 um 00:33 schrieb Junio C Hamano:
Show 10 quoted lines
> René Scharfe <l.s.r@web.de> writes:
> 
>> 	@ depends on r @
>> 	expression E;
>> 	@@
>> 	- *&
>> 	  E
> 
> I guess my source of the confusion is that the tool that understands
> the semantics of the C language still needs to be told about that.

Understanding that E and *&E have the same type does not imply (for a machine) that E alone is preferable.

Show 17 quoted lines
> I was hoping that something that understands C only needs to be told
> only a single rule:
> 
> 	type T
> 	T src, dst
> 
> 	-memcpy(&dst, &src, sizeof(dst));
> 	+dst = src;
> 
> and then can apply that rule to this code in four ways:
> 
> 	struct foo A, *Bp;
> 
> 	memcpy(Bp, &A, sizeof(*Bp));
> 	memcpy(Bp, &A, sizeof(A));
> 	memcpy(&src, dstp, sizeof(A));
> 	memcpy(&src, dstp, sizeof(*Bp));
I guess src is A and dstp is Bp?

Coccinelle does not know that the sizeof expressions are equivalent, but you could normalize them with an additional rule and then use a single memcpy transformation like this:

	@ normalize_sizeof @
	type T;
	T var;
	@@
	- sizeof(var)
	+ sizeof(T)
	@ r @
	type T;
	T *dst;
	T *src;
	@@
	- memcpy(dst, src, sizeof(T));
	+ *dst = *src;
	@ depends on r @
	expression E;
	@@
	- *&
	  E
That would give you what you expected here:
Show 8 quoted lines
> to obtain its rewrite:
> 
> 	struct foo A, *Bp;
> 
> 	*Bp = A;
> 	*Bp = A;
> 	A = *Bp;
> 	A = *Bp;

But that normalization rule would be applied everywhere because it's so broad, and that's probably not what we want. You could replace it with an isomorphism like this one:

	Expression
	@@
	type T;
	T E;
	@@
	sizeof(T) => sizeof E

In your example it allows you to specify sizeof(struct foo) (or a generic sizeof(T) as in rule r above) in the semantic patch and Coccinelle would let that match sizeof(A) and sizeof(*Bp) in the C file as well.

Isomorphisms are kept in a separate file, the default one is /usr/lib/coccinelle/standard.iso on my machine and you can chose a different one with --iso-file. Perhaps we want to have our own for git, but we'd need to synchronize it with upstream from time to time.

There is already a very similar isomorphism rule in the default file, but I don't think I understand it:

	Expression
	@ sizeof_type_expr @
	pure type T; // pure because we drop a metavar
	T E;
	@@
	sizeof(T) => sizeof E

In particular I'm a bit worried about the lack of documentation for "pure", and I don't understand the comment. There's another comment at the top of another rule in the same file:

// pure means that either the whole field reference expression is dropped, // or E is context code and has no attached + code // not really... pure means matches a unitary unplussed metavariable // but this rule doesn't work anyway

Hmm.

Here's an isomorphism that allows you to use "sizeof *src" (the third part for T is not strictly needed for your example):

	Expression
	@ sizeof_equiv @
	type T;
	T E1, E2;
	@@
	sizeof E1 <=> sizeof E2 <=> sizeof(T)

That's the kind of bidirectional equivalence you expected to be part of Coccinelle's standard set of rules, right? With that rule in place the following semantic patch matches your four cases:

	@ r @
	type T;
	T *dst;
	T *src;
	@@
	- memcpy(dst, src, sizeof *dst);
	+ *dst = *src;
	@ depends on r @
	expression E;
	@@
	- *&
	  E

But I'd be careful with that as long as "pure" is present in that standard rule and not fully understood. The isomorphism sizeof_equiv doesn't seem to cause any trouble with our existing semantic patches and the code in master, though.

René
Previous: Junio C HamanoNext: Ramsay Jones
Message 33 of 36 in “Travis: also test on 32-bit Linux”
  1. Travis: also test on 32-bit LinuxJohannes Schindelin, Feb 28, 2017
  2. Johannes SchindelinFeb 28, 2017
  3. Junio C HamanoMar 2, 2017
  4. Travis: also test on 32-bit LinuxLars Schneider, Mar 2, 2017
  5. Johannes SchindelinMar 2, 2017
  6. Lars SchneiderMar 2, 2017
  7. Johannes SchindelinMar 2, 2017
  8. Christian CouderMar 2, 2017
  9. Junio C HamanoMar 2, 2017
  10. Johannes SchindelinMar 3, 2017
  11. Junio C HamanoMar 3, 2017
  12. Junio C HamanoMar 4, 2017
  13. Junio C HamanoMar 4, 2017
  14. Lars SchneiderMar 4, 2017
  15. Vegard NossumMar 4, 2017
  16. Vegard NossumMar 4, 2017
  17. Vegard NossumMar 4, 2017
  18. Jeff KingMar 5, 2017
  19. line-log: use COPY_ARRAY to fix mis-sized memcpyJeff King, Mar 5, 2017
  20. Vegard NossumMar 5, 2017
  21. Jeff KingMar 5, 2017
  22. René ScharfeMar 10, 2017
  23. Jeff KingMar 10, 2017
  24. René ScharfeMar 10, 2017
  25. Jeff KingMar 10, 2017
  26. René ScharfeMar 10, 2017
  27. Jeff KingMar 10, 2017
  28. René ScharfeMar 10, 2017
  29. Junio C HamanoMar 10, 2017
  30. Jeff KingMar 10, 2017
  31. René ScharfeMar 10, 2017
  32. Junio C HamanoMar 10, 2017
  33. René ScharfeMar 11, 2017
  34. Ramsay JonesMar 2, 2017
  35. Lars SchneiderMar 5, 2017
  36. Ramsay JonesMar 5, 2017

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.