NO

Author Topic: Compiler Warning  (Read 4826 times)

Offline John Z

  • Member
  • *
  • Posts: 865
Compiler Warning
« on: March 30, 2022, 01:35:19 PM »
if you declare
Code: [Select]
HICON hIcon = NULL;
then within
Code: [Select]
case WM_INITDIALOG:
   hIcon = LoadImage( ghInstance,MAKEINTRESOURCE(JGZ),IMAGE_ICON,
                           32,32,LR_SHARED);
                           
then within
Code: [Select]
case WM_CLOSE:
   if (hIcon) {DestroyIcon(hIcon);}
        
The compiler generates a Warning message for > 'if (hIcon) {DestroyIcon(hIcon);}'
: warning #2154: Unreachable code.
 
Then change the declare to
Code: [Select]
HICON hIcon;
The compiler generates a Warning message for > 'HICON hIcon;'
:warning #2229: Local 'hIcon' is potentially used without being initialized.

Is there a third way that has no warning ?  I use warnings Level 2 and C11.

John Z

Offline frankie

  • Global Moderator
  • Member
  • *****
  • Posts: 2113
Re: Compiler Warning
« Reply #1 on: March 30, 2022, 03:22:22 PM »
There is something wrong here.
You should get the message:
Code: [Select]
: warning #2154: Unreachable code. because the compiler evaluates that the the condition:
Code: [Select]
hIcon != NULL is never met.
For this reason the whole block:
Code: [Select]
if (hIcon) {DestroyIcon(hIcon);} is removed from compilation output as "dead code".
This could happen if:
  • hicon is a local variable
  • No change happens to its value so the compiler can safely assume that it will always be null.
To understand if these conditions are really met, and this is not a compiler bug, you should post the smallest piece of complete code that shows the problem.

If tis is a bug you can try as workaround:
Code: [Select]
volatile HICON hIcon;The 'volatile' qualifier informs the compiler that the variable can be changed by external causes, and for this reason no assumptions on its value have to be made.
« Last Edit: March 30, 2022, 03:45:30 PM by frankie »
"It is better to be hated for what you are than to be loved for what you are not." - Andre Gide

Offline John Z

  • Member
  • *
  • Posts: 865
Re: Compiler Warning
« Reply #2 on: March 31, 2022, 02:40:57 AM »
Yes I understand why, but one or the other should not be in error I think.

static HICON hIcon = NULL;

Also 'fixes' (no warnings) it but clearly not that desirable.

I'll try to generate a simple example. 

John Z

Offline frankie

  • Global Moderator
  • Member
  • *****
  • Posts: 2113
Re: Compiler Warning
« Reply #3 on: March 31, 2022, 09:33:07 AM »
I'll try to generate a simple example. 

John Z
Yes please, because I can't reproduce such error with PellesC V11.
"It is better to be hated for what you are than to be loved for what you are not." - Andre Gide

Offline John Z

  • Member
  • *
  • Posts: 865
Re: Compiler Warning
« Reply #4 on: March 31, 2022, 01:00:31 PM »
Frankie, Thanks for the reminder to include the Pelles C version too.

 Initial work was from version 10.  I'm a slow adopter  :)

However attached is a simple program test case which I ran in version 10 and version 11.  The reported
warnings are somewhat different from each but both versions show the only way to satisfy the compiler (ie no warning)
is to use 'static HICON hIcon;' or 'volatile HICON hIcon = NULL;'

IMO should not be the case because clearly
Code: [Select]
hIcon = LoadImage( ghInstance,MAKEINTRESOURCE(JGZ),IMAGE_ICON,
                           32,32,LR_SHARED);
will affect the value of hIcon.

Just uncomment the variable declare at the top of MainDlgProc and compile.  The warning line number I put in the comments will be off a bit because I added comments while testing.  There are 5 test cases.  Should have been 6
I forgot to include 'static HICON hIcon = NULL;'


John Z


Offline MrBcx

  • Global Moderator
  • Member
  • *****
  • Posts: 195
    • Bcx Basic to C/C++ Translator
Re: Compiler Warning
« Reply #5 on: March 31, 2022, 05:41:51 PM »
This works for me on V11

HICON hIcon = {0};
Bcx Basic to C/C++ Translator
https://www.BcxBasicCoders.com

Offline frankie

  • Global Moderator
  • Member
  • *****
  • Posts: 2113
Re: Compiler Warning
« Reply #6 on: March 31, 2022, 05:45:23 PM »
Ok John I see now.
The compiler seems correct, there is a flaw in the logic of the function 'MainDlgProc'.
When you declare:
Code: [Select]
HICON hIcon = NULL; or
Code: [Select]
HICON hIcon;You are creating an automatic variable that will be lost as soon as execution flow exits the function. This imply that the value of the variable 'hicon' exists for a single switch case per call.
So you can have:
  • When 'uMsg' is 'WM_INITDIALOG' you are assigning a value to it, that will be lost on return.
  • When 'uMsg' is 'WM_CLOSE':
    • If 'hicon' isn't initialized you're using a dangling value for the 'if' test (warning #2116)
    • if 'hicon' is initialized to NULL the comparison is constant and always false and the conditional code never executed ('warning #2154: Unreachable code' and 'warning #2154: Unreachable code')
The problem is essentially related to the scope of the variable. Probably this piece of code was originally positioned in the 'WinMain' function and its scope was persistent for the whole program execution ('WinMain' scope end when program ends). Moving the code to a function the scope was modified and local to the function itself.
Making it 'static' guarantee that the variable exists and retain its value between calls, miming the functionality as when declared in the 'WinMain'.

Anyway something that I've not fully understand happens using the 'volatile' qualifier.
Using:
Code: [Select]
volatile HICON hIcon = NULL; the compiler doesn't complain, while omitting the initialization to 'NULL' V11 warns about constant compare. What's the rationale behind this?
Anyway making it 'static' no more complains are made.

"It is better to be hated for what you are than to be loved for what you are not." - Andre Gide

Offline John Z

  • Member
  • *
  • Posts: 865
Re: Compiler Warning
« Reply #7 on: March 31, 2022, 10:45:04 PM »
Thanks frankie,

The code didn't come from anywhere other than my mind. ..... ;)

I guess it is my misunderstanding coming from a C procedural flow world to a Windows event driven world.
I thought I could use WM_INITDIALOG to set the hIcon once and it would be there for the duration of the existence
of the dialog, but I knew it needed to be destroyed before closing the dialog.  I had ended up using Static in the code but thought, as I was trying to find a bug, that this might be my bug source.  So since the only dumb question is the one you don't ask, I figured I'd better check.   :)

Appreciate the help,
John

Offline frankie

  • Global Moderator
  • Member
  • *****
  • Posts: 2113
Re: Compiler Warning
« Reply #8 on: April 01, 2022, 12:01:40 PM »
John you're always welcome.
It is good IMHO to talk and discuss some detail that could be interesting for many, also considering that more skilled is the programmer more often she/he stops at very simple problems because of the mind orientation that looks always for major issues...  ;D
It is the human nature indeed at last...  :(
On my side I still have doubts about the compiler warnings when the 'volatile' qualifier is used, as I reported in my previous post.
« Last Edit: April 01, 2022, 12:05:54 PM by frankie »
"It is better to be hated for what you are than to be loved for what you are not." - Andre Gide

Grincheux

  • Guest
Re: Compiler Warning
« Reply #9 on: April 02, 2022, 12:14:13 PM »
Quote
[size=0px]The compiler generates a Warning message for > 'if (hIcon) {DestroyIcon(hIcon);}'[/size][/size][size=0px]: warning #2154: Unreachable code.[/size]
[size=0px]

Yes because it is declared as NULL

If hIcon is local this is normal[/size]