C and MISRA, blues... (arithmetic shifts)

In message , Wilco Dijkstra writes

This is true in practice.

Yes. Actually as long as the behaviour of the compiler is known documented and repeatable the standard does not matter in reality. Most embedded compilers are not ISO-C99 compliant but mostly ISO-C90/95 with compiler and target extensions.

I assume you mean ISO-C compiler. Which standard? C90, C95, C99?

I do have an email where a user says:

"We have moved from abc compiler to XYZ compiler. We used to compile with abc and get no errors. We now using xyz compiler we get lots of errors. We think this is because your xyz compiler is more strict than the abc compiler.

Please can you supply us a version of the xyz compiler with a less strict parser."

Yes I do have all the names.

--
\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\
\/\/\/\/\ Chris Hills  Staffs  England     /\/\/\/\/
\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/
Reply to
Chris H
Loading thread data ...

Echoing the question. What do you need them for that's not covered by a divide by a power of 2?

What about

int asr( int x, unsigned int shift) { unsigned int temp;

temp=(unsigned int)x;

if( x < 0) { temp = ~((~temp) >> shift); } else { temp >>= shift; } return (int)temp; }

Does that cover all the cases? For a negative value it converts the sign extend to a zero extend and the positive case works as usual.

Commenting left to the user.

It's small enough you could probably make a macro (with some loss of clarity) and for constant shifts a good compiler might end up optimizing it back to a ASR. Maybe?

Or, take the simple way out and declare an exception (whatever the term is MISRA uses for a formal waiver of a rule). As I recall they can apply at indivual case, project level or as company policy as an exception. They do need to be documented though.

Robert

** Posted from
formatting link
**
Reply to
Robert Adsett

In message , FreeRTOS.org writes

*Personally* I would not disagree with that. Strict blind adherence to any set of (arbitrary) rules should avoided. There is AFAIK in MISRA-C room for deviations. If you can document a reason (that will stand up in court in 3 years time) for doing something different then do that.
  • All comments here are purely personal and not representing any company, organisation or body other than mine.

Sounds very sensible to me.

You do need to know exactly what your compiler will do. It is amazing how many people make blind assumptions about C compilers.

Sounds good to me. You have documented the behaviour of the tools and reasons for doing "unsafe" things because in this particular instance it is the best solution and is not "unsafe" bea.

Precisely...... The point is that behaviour is EXACTLY as expected and fully documented. Ie reliable, repeatable and safe as reasonably practicable.

Rule is rules guv... more than my jobs worff to....

:-)

--
\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\
\/\/\/\/\ Chris Hills  Staffs  England     /\/\/\/\/
\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/
Reply to
Chris H

... snip ...

The only 'required' rules are those of the C standard.

--
 [mail]: Chuck F (cbfalconer at maineline dot net) 
 [page]: 
            Try the download section.


** Posted from http://www.teranews.com **
Reply to
CBFalconer

In message , Richard Phillips writes

This is true.

Maybe. IT was AFAIK Dykstra who said goto was bad and no one has challenged that with a convincing strategy for using goto. Mainly because the majority who do use it tend to miss use it. So it should not normally be used but...

All of the MISRA rules are good *some* of the time. Where they are not it is up to you to come up with a project specific reason why not.

I know what you mean it is the "tick the box" brigade who want to say we are MISRA compliant without actually using any Engineering thought on it.

Hence MIStRAy-C A spoof on MISRA-C

formatting link

I personally believe this is the way it is meant to be used.

Any suggestions on how the MISRA team can stop people doing this All methods must be legal under the UN human rights and Geneva conventions. Water-boarding or stringing up by their thumbs for recalcitrant programmers and managers may be deserved and satisfying but we can't writ it in to a coding standard :-)

It was required and advisory. IE those that should normally be used and those which are useful a lot of the time.

Any suggestions for a different nomenclature?

--
\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\
\/\/\/\/\ Chris Hills  Staffs  England     /\/\/\/\/
\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/
Reply to
Chris H

writes

exact rules off-hand - perhaps that's

anyway?!?

and repeatable the standard does not

mostly ISO-C90/95 with compiler and target

Much of this has to be documented to be conformant. Most compilers also document details of structure layout, language extensions, ABIs etc.

I have seen very little C99-only code, although most compilers do support various C99 features in C90 mode. Long long is a good example, we did it years before C99.

millions of

compiler...

This was C89, the first ANSI C standard. We used -ansi and -c89 options for a long time, even after ISO C99.

and get no errors. We now using xyz

more strict than the abc compiler.

parser."

Sounds fairly typical of a customer indeed. It's impossible to even try to talk them into fixing their code, as it works on any other compiler they tried. So you've got to fix the compiler or go out of business. Not a hard choice...

Wilco

Reply to
Wilco Dijkstra

/* Not sure whether that passes your MISRA checker: */ return (int) ((unsigned long long) value >> shift);

That aside, MISRA usually allows you to deviate from a rule if you have a good reason. This is to make you think about whether you really need it. Arithmetic shifts would be a good thing to answer "yes" to that question.

The function could finally even look like this: int ArithmeticShiftRight (int value, unsigned int shift) { #if ((-1) >> 1) == -1 return value >> shift; #else # error Port me! #endif } which would make your code portable under all practical definitions known to me.

Stefan

Reply to
Stefan Reuther

You can't know that. You can't know if two things are unequal without a reliable source defining the value for either of them. -7>>1 causes undefined behaviour in a C program. So every assumption about its result is wrong by default.

And guess what: the result of (-7/2) is unkown, too! Technically, at least as of C90, which still is the effectively valid definition for many of us, it's implementation-defined whether signed division rounds towards negative infinity or zero. So it could be -4 as easily as it could be -3. C99 changed this. Now it's required to be -3.

Reply to
Hans-Bernhard Bröker

_Nothing_ about shifts of negative values is defined _at_all_ in C. For all you know, the machine could catch fire if ever you try it on a Tuesday between 12:34:56 h and 12:36:54h (Hawaiian time).

Rounding as a concept is inapplicable to non-arithmetic operators. There is no full-precision intermediate result, thus nothing to be rounded.

Not surprisingly --- nothing there to be remembered.

You betcha.

Reply to
Hans-Bernhard Bröker

That's beside the point --- shifting is not an arithmetic operation.

Nor is there even a definition of "correct" in place for shifting negative numbers. If there were, there would never been a need to invent the terms "arithmetic shift" and "logical shift".

The problem is not with compiling the code --- it's what the compiled code will actually do.

Reply to
Hans-Bernhard Bröker

IMHO, gotos are fine for jumping forward, but jumping backwards makes it very hard to follow the program logic. Some looping control structure can be used to repeat previously executed code.

I have used this principle since the FORTRAM IV days, in which the only block control structure was the DO-loop :-).

Paul

Reply to
Paul Keinanen

With arithmetic I meant all operators, including logical, relational, additive, conversions etc.

numbers. If there were, there would never

The correct way to shift a signed number is to use an arithmetic shift. The correct way to shift an unsigned number is to use a logical shift. This stuff is pretty trivial and well defined. No compiler gets this wrong.

will actually do.

You obviously compile to execute... It's well defined what a compiler will do. If it didn't give the right answer the compiler would be considered broken.

Wilco

Reply to
Wilco Dijkstra

Yes, you're formally right of course. I have no reference except what works in practice.

Name me one CPU/system that:

a. Does signed arithmetic in one's complement. b. a c-compiler exists for that architectue. c. Has any significance except nostalgia/historic reasons.

Yes, I'm nitpicking, but so are you :-)

Nils

Reply to
Nils

... snip ...

If your errors/warnings emit a number, and then haul up an error message via an index into an auxiliary file, you can soften those messages as much as you wish without doing anything special. That is also language independant.

--
 [mail]: Chuck F (cbfalconer at maineline dot net) 
 [page]: 
            Try the download section.


** Posted from http://www.teranews.com **
Reply to
CBFalconer

If so, you just lost this nit-picking contest. ;->

"significance except nostalgia/history" is completely worthless as a nit-picking tool. It's an impossibly vague phrase that, if you really look at it, means nothing at all.

Reply to
Hans-Bernhard Bröker

Oh well.

But why does for example the java language explicitly defines a signed right-shift operator? I think the language designers learned from the c-language and didn't wanted to make the same mistake again. After all a compiler for a hypotetical CPU that can't do the arithmetic shift can simulate the operation.

You've asked elsewhere why one would do binary arithmetic on signed intergers at the first place. I agree with you that you normally don't need that, but there are exceptions. Here is just one:

I have to work on a integer-only CPU and have performance-goals that I can't reach with soft-float. My problem calls for more than just integer arithmetic.

Requirements are tight, as usual. So what do I do? I write all my arithmetic with block-floating-point. That makes the difference in performance that brings me over my mips-limit that was negotiated. It makes my client happy as well. I do need some signed binary arithmetic to get the magic happen though.

Fortunately you can explain such niffy details to the code-review guy and get a grant for a misra-warning, but it is cunmbersome to do it again and again.

Nils

Reply to
Nils

Richard Phillips schrieb:

100% agree. But I think you miss a very important "real world" part of the entire MISRA thing:

You can't simply write "code should not suck" into a contract. If you write a piece of code for a company that does safety-critical stuff you'll better have some way to measure the code-quality.

This saves both parties of the contract and makes sure you don't get into an endless "please change this, I don't like that either, we got a warning here, what do you do there" loop.

Noone want's that. It is a efficient way to burn money and make sure that the final product never sees the light of day if you don't define some kind of standard. In my case that's MISRA with the bullshit omitted and some other bullshit added Since I deliver code the recommendation becomes a duty. With all pros and cons.

Btw. I dig most of the recommendations. And I didn't had much problems to adopt my code. It was pretty good when I started to care about compliance.

There have been some things that made my code more unreadable. Some changes even came with a performance costs, but on the other hand I had to refactor and re-thing several functions that I would haven't touched.

I came up with a much easier and more performant way to express the same thing. And this is good.

Nils

Reply to
Nils

Jep! I have to agree. I just wanted to make sure you don't bring obsolete russian architectures into the discussion that do trenary arithmetic :-)

Ok. Ignore point c. Any answer to points a and b of my list?

Nils

Reply to
Nils

... snip ...

Yes, you are, but no, he's not. Shifts on negative values are undefined behaviour on any system.

--
 [mail]: Chuck F (cbfalconer at maineline dot net) 
 [page]: 
            Try the download section.


** Posted from http://www.teranews.com **
Reply to
CBFalconer

I totally agree; that's exactly my attitude. MISRA is good, defensive common sense designed by a committee ;).

Re the OP's issue: I'd isolate myself from the underlying language (whatever it may be) by decomposition - by encapsulating the function in a subroutine. A shift is a trick for a fast integer divide or mulitply by 2. So I'd write something like:

int fast_divide_by_two( int )

and in the simplest case, I'd use a shift. On MISRA, I'd use something more complex - but it'd still be readable, since my intention is clear. (Hell, use a macro if you prefer. Hell, factor it out and make it platform-specific. Hell, so long as it's clear, I don't care about complex - I can always decompose it out.)

/me now poorer by 2c

Steve

Reply to
Steve at fivetrees

ElectronDepot website is not affiliated with any of the manufacturers or service providers discussed here. All logos and trade names are the property of their respective owners.