I'm trying to edit my tasks.json and/or launch.json to output warnings gcc would usually show when compiling C code with -Wall and -Wextra flags using Run Without Debugging.
When using the the Run Without Debugging option in VSCODE it seems to compile the program using the flags set in my workspace tasks.json file but it doesn't show me the output of gcc.
There's a Task - build active file-tab in the terminal section but it just shows:
> Executing task: C/C++: gcc build active file <
Starting build...
Build finished successfully.
Terminal will be reused by tasks, press any key to close it.
Example code:
#include <stdio.h>
int main(void)
{
int ten = 10;
int two = 2;
printf("Doing it right:\t");
printf("%d minus %d is %d\n\n", ten, 2, ten - two);
printf("Doing it wrong:\t");
printf("%d minus %d is %d\n",ten); // Two arguments missing
return 0;
}
Example of the desired output upon compiling:
example.c: In function ‘main’:
example.c:13:23: warning: format ‘%d’ expects a matching ‘int’ argument [-Wformat=]
13 | printf("%d minus %d is %d\n",ten); // Two arguments missing
| ~^
| |
| int
example.c:13:29: warning: format ‘%d’ expects a matching ‘int’ argument [-Wformat=]
13 | printf("%d minus %d is %d\n",ten); // Two arguments missing
| ~^
| |
| int
Related
following code when included in kernel.h
#define MEMORY_GB 1
#define MEMORY_SIZE 100000*1024*MEMORY_GB
char memory[MEMORY_SIZE];
causes gcc to stop working
make: *** [kernel.x86_64.elf] Error 1
In file included from kernel.c:111:
libs/graphics.h: At top level:
libs/graphics.h:12:6: warning: conflicting types for 'cleardevice'
12 | void cleardevice(){
| ^~~~~~~~~~~
kernel.c:90:9: note: previous implicit declaration of 'cleardevice' was here
90 | cleardevice();
| ^~~~~~~~~~~
In file included from kernel.c:111:
libs/graphics.h:28:6: warning: conflicting types for 'setbkcolor'
28 | void setbkcolor(uint32_t color){
| ^~~~~~~~~~
kernel.c:89:9: note: previous implicit declaration of 'setbkcolor' was here
89 | setbkcolor(YELLOW);
| ^~~~~~~~~~
In file included from kernel.c:114:
idt.h:25:6: warning: conflicting types for 'InitializeIDT'
25 | void InitializeIDT(){
| ^~~~~~~~~~~~~
kernel.c:69:5: note: previous implicit declaration of 'InitializeIDT' was here
69 | InitializeIDT();
| ^~~~~~~~~~~~~
In file included from kernel.c:114:
idt.h: In function 'InitializeIDT':
idt.h:38:2: warning: implicit declaration of function 'RemapPic' [-Wimplicit-function-declaration]
38 | RemapPic();
| ^~~~~~~~
idt.h: At top level:
idt.h:46:6: warning: conflicting types for 'RemapPic'
46 | void RemapPic(){
| ^~~~~~~~
idt.h:38:2: note: previous implicit declaration of 'RemapPic' was here
38 | RemapPic();
| ^~~~~~~~
In file included from kernel.c:113:
core/memory.h: In function 'malloc':
core/memory.h:27:1: warning: control reaches end of non-void function [-Wreturn-type]
27 | }
| ^
In file included from kernel.c:115:
drivers/ps2/keyboard.h: In function 'scanCodeToKey':
drivers/ps2/keyboard.h:9:1: warning: control reaches end of non-void function [-Wreturn-type]
9 | }
on terminal there is no errors outputted by gcc in first place which is odd it returns with 1 as exit code which make complains about that, but when array size changed to 1 it magically works aren't there is no limit for array size in C? Another odd thing is even though this fail happens in build time and there shouldn't be a issue with the kernel itself
Another odd finding when i remove the macros and directly write with a random length like 400
char memory[400];
again same issue huh but
char memory[1];
works perfectly fine
Despite my attempts at googling why something like happens there was no results.
Here is some information about my system:
Build Env: Linux Lubuntu
Compiler: Gnu Gcc cross compiler x86_64-elf-gcc (GCC) 10.2.0
Sidenote: Kernel was working perfectly just the issue is that weird array problem on the memory manager
The code here is a code from a website. Since I was facing an issue with my origin code, I ended up trying this implementation from a website. But turns out I have the same issue with this program too
#include <stdio.h>
#include <stdlib.h>
int main()
{
int num;
FILE *fptr;
if ((fptr = fopen("D:\\TestFile\\test.txt","r")) == NULL){
printf("Error! opening file\n");
perror(fptr);
// Program exits if the file pointer returns NULL.
exit(1);
}
fscanf(fptr,"%d", &num);
printf("Value of n=%d\n", num);
printf("%s\n", fptr);
fclose(fptr);
return 0;
}
I am stuck with the if condition i.e., whatever I do I am not able to read the file except the root directory. Even though I specify the path, it still looks for the file under root directory.
I am not sure why it's not working, provided the same code works fine in Linux
I see 2 mistakes, the one related to perror mentioned in the comments, and the last printf. Now if the program is still not working, it could be interesting to check the error or to get the program output.
#include <stdio.h>
#include <stdlib.h>
int main()
{
int num;
FILE *fptr;
if ((fptr = fopen("D:\\TestFile\\test.txt","r")) == NULL){
// printf("Error! opening file\n");
// perror(fptr); // MISTAKE-1: perror parameter is a string
perror("Error! opening file");
// Program exits if the file pointer returns NULL.
exit(1);
}
fscanf(fptr,"%d", &num);
printf("Value of n=%d\n", num);
//printf("%s\n", fptr); // MISTAKE-2: fptr is not a string
fclose(fptr);
return 0;
}
the posted code does not cleanly compile!
Here is the results of compiling with many of the warnings enabled:
gcc -ggdb3 -Wall -Wextra -Wconversion -pedantic -std=gnu11 -c "untitled1.c" -o "untitled1.o"
untitled1.c: In function ‘main’:
untitled1.c:11:16: warning: passing argument 1 of ‘perror’ from incompatible pointer type [-Wincompatible-pointer-types]
11 | perror(fptr);
| ^~~~
| |
| FILE * {aka struct _IO_FILE *}
In file included from untitled1.c:1:
/usr/include/stdio.h:775:33: note: expected ‘const char *’ but argument is of type ‘FILE *’ {aka ‘struct _IO_FILE *’}
775 | extern void perror (const char *__s);
| ~~~~~~~~~~~~^~~
untitled1.c:19:13: warning: format ‘%s’ expects argument of type ‘char *’, but argument 2 has type ‘FILE *’ {aka ‘struct _IO_FILE *’} [-Wformat=]
19 | printf("%s\n", fptr);
| ~^ ~~~~
| | |
| | FILE * {aka struct _IO_FILE *}
| char *
Compilation finished successfully.
Note; the statement: Compilation finished successfully. just means the compiler applied some work around to each of the problems. It does NOT mean the correct code was produced.
In order to make a good timing in an emulator, I have to wait for around 50 microseconds.
When I use nanosleep, for example with a duration of 10 microsecs, I measure a delay of 15 millisec ! I use mingw on windows with the following example code :
#include <stddef.h>
#include <time.h>
#include <stdio.h>
int main()
{
struct timespec startx, endx;
struct timespec req={0};
req.tv_sec=0;
req.tv_nsec=10000; // 10_000 ns = 10 microseconds
for (int i=0; i<10; i++)
{
clock_gettime(CLOCK_MONOTONIC, &startx);
nanosleep(&req, NULL);
clock_gettime(CLOCK_MONOTONIC, &endx);
if (endx.tv_sec-startx.tv_sec)
printf("%li microsecs\n",((endx.tv_nsec-startx.tv_nsec)/1000)+1000000);
else
printf("%li microsecs\n",(endx.tv_nsec-startx.tv_nsec)/1000);
}
return 0 ;
}
And the result is :
12528 microsecs
19495 microsecs
14890 microsecs
14229 microsecs
14657 microsecs
14824 microsecs
14724 microsecs
21074 microsecs
13697 microsecs
13893 microsecs
I guess I'm wrong somewhere....
If someone has an idea. I could also avoid the problem with a "do nop while (end-start) < 50usec"...
Thanks.
When I run the posted code through a compiler (gcc) the compiler outputs the following:
gcc -ggdb3 -Wall -Wextra -Wconversion -pedantic -std=gnu11 -c "untitled1.c" -o "untitled1.o"
untitled1.c: In function ‘main’:
untitled1.c:16:57: error: ‘err’ undeclared (first use in this function)
16 | if (nanosleep(&req, NULL)) printf("err : %i\n", err);
| ^~~
untitled1.c:16:57: note: each undeclared identifier is reported only once for each function it appears in
untitled1.c:18:18: warning: format ‘%d’ expects argument of type ‘int’, but argument 2 has type ‘__syscall_slong_t’ {aka ‘long int’} [-Wformat=]
18 | printf("%d microsecs %d\n",(endx.tv_nsec-startx.tv_nsec)/1000, endx.tv_sec-startx.tv_sec);
| ~^ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
| | |
| int __syscall_slong_t {aka long int}
| %ld
untitled1.c:18:31: warning: format ‘%d’ expects argument of type ‘int’, but argument 3 has type ‘__time_t’ {aka ‘long int’} [-Wformat=]
18 | printf("%d microsecs %d\n",(endx.tv_nsec-startx.tv_nsec)/1000, endx.tv_sec-startx.tv_sec);
| ~^ ~~~~~~~~~~~~~~~~~~~~~~~~~
| | |
| int __time_t {aka long int}
| %ld
Compilation failed.
When compiling, always enable the warnings, then fix those warnings.
to start, suggest casting the result of the call to time() to be a long int
as to your question:
context switches take time AND the cpu(s) are probably busy with other tasks AND the task scheduler only looks at the list of tasks ready to run periodically , so your request will not be immediately serviced.
to obtain a more accurate timing, do not depend on the OS. Rather use one of the hardware timers to produce a interrupt event when you want the elapsed time to expire. Then use an interrupt handler to handle the interrupt event from the hardware timer.
I need a complex library for some stuf in c++ or c.
So I found some useful tooltip in linux.
man complex
documentation have good example like this:
#include <math.h> /* for atan */
#include <stdio.h>
#include <complex.h>
int
main(void)
{
double pi = 4 * atan(1.0);
double complex z = cexp(I * pi);
printf("%f + %f * i\n", creal(z), cimag(z));
}
everything goes well...
But I took error every time which I tried.
> Executing task: /usr/bin/g++ -g '/home/max/Documents/c_expls/test2.cpp' -o '/home/max/Documents/c_expls/test2' <
/home/max/Documents/c_expls/test2.cpp: In function ‘int main()’:
/home/max/Documents/c_expls/test2.cpp:10:17: error: expected initializer before ‘z’
10 | double complex z = cexp(I * pi);
| ^
/home/max/Documents/c_expls/test2.cpp:11:32: error: ‘z’ was not declared in this scope
11 | printf("%f + %f * i\n", creal(z), cimag(z));
| ^
The terminal process "/bin/bash '-c', '/usr/bin/g++ -g '/home/max/Documents/c_expls/test2.cpp' -o '/home/max/Documents/c_expls/test2''" terminated with exit code: 1.
Terminal will be reused by tasks, press any key to close it.
I edited code a little bit, like adding double complex z etc.. but same machine... same error...
I think my gcc installation have lacks component. beause I tried Code::Blocks
Do you have an idea,
why my gcc doesn't know this declaration?
You need to compile with gcc and specify that you want to use the C99 standard or higher -std=c99.
For C++, use std::complex.
You need to link against the math library with the flag -lm
Using exactly your code in a file called test.c I compiled with:
gcc -o test test.c -lm
Running the binary gives the output:
./test
-1.000000 + 0.000000 * i
We have a vendor supplied api which has a struct defined as
typedef struct
{
char duo_word[8];
} duo_word;
They send us data in this structure which we then have to pass to our java app through jni.
printf("Number: : %i\n", duo_word_inst);
prints the correct int value e.g 52932, but
printf("Number: : %s\n", duo_word_inst);
prints nothing.
More over if I use jni code below my java process receives gibberish.
jstring jstrBuf = (*env)->NewStringUTF(env, (char*)(duo_word_inst));
(*env)->SetObjectField(env, *ret_obj, fld_id, jstrBuf);
sends gibberish to java e.g ÄÎ
// I have got some example data captured from VS debugger below.
duo_word duo_word_inst = { .duo_word = { 'º', '\b', '\x1', '\0', 'À', '\xe', '2', 'a' } };
printf(" %i ", duo_word_inst); // gives 67770 which is correct.
My C skills are very elementary so I would really appreciate if some one could point out the silliness I am doing here. Thanks,
I'll give it a shot. I tried your code, but don't get the same behavior
#include <stdio.h>
typedef struct
{
char duo_word[8];
}duo_word_t;
int main (int p_argc, char *p_argv[])
{
duo_word_t l_duo_word =
{
.duo_word = {'1','2','3','4'}
};
/** Works fine. */
printf("value s: %s\n", l_duo_word.duo_word);
/** Doesn't work. */
printf("value i: %i\n", l_duo_word.duo_word);
return 0;
}
output:
$ ./test
value s: 1234
value i: 159754736
I don't see why using the format specifier %s, returns an empty string in your case.
Besides that I don't get why you are using %i. You should get a warning when doing so:
$ gcc test.c -Wall -Wpedantic -o test
test.c: In function ‘main’:
test.c:19:16: warning: format ‘%i’ expects argument of type ‘int’, but argument 2 has type ‘char *’ [-Wformat=]
printf("value i: %i\n", l_duo_word.duo_word);
Could you show how you initialize your structure?