Doing an OS programming assignment using semaphores and POSIX threads. Here's my code:
#include <pthread.h>
#include <semaphore.h>
sem_t mutex, to_b, to_a;
int main()
{
// Initialize semaphores
sem_init(&mutex, 0, 1);
sem_init(&to_b, 0, 0);
sem_init(&to_a 0, 0);
}
Compiling with gcc main.c -lpthread I get:
main.c: In function 'main':
main.c:11:24: error: expected ')' before numeric constant
main.c:11:24: error: too few arguments to function 'sem_init'
/usr/include/semaphore.h:37:12: note: declared here
Any idea what could cause this? I'm definitely calling sem_init correctly.
There is a comma missing in
sem_init(&to_a 0, 0);
It should be
sem_init(&to_a, 0, 0);
sem_init(&to_a 0, 0);
^
You're just missing a comma.
So look at the error: main.c:11:24: error: too few arguments to function 'sem_init'
Line 11 has a problem, it has "too few arguments". You're making the same call on line 10 and 9 right? but no such error, so take a careful look, character for character between line 10 and line 11.
You'll see you missed a comma:
sem_init(&to_b, 0, 0);
sem_init(&to_a 0, 0); // see it's shorter?
Should be:
sem_init(&to_a, 0, 0);
Related
This question already has answers here:
How do function pointers in C work?
(12 answers)
Closed last month.
I have a C program in which this pointer to function is defined. And i am getting compilation error, what am i doing wrong?
typedef long (*myfunc)(long, long, long, long);
void mytest() {
(*myfunc)(0, 0, 0, 0);
myfunc(0, 0, 0, 0);
}
output from gcc ./test.c
$ gcc ./test.c
./test.c: In function ‘mytest’:
./test.c:106:5: error: expected expression before ‘myfunc’
106 | (*myfunc)(0, 0, 0, 0);
| ^~~~~~
./test.c:107:10: error: expected identifier or ‘(’ before numeric constant
107 | myfunc(0, 0, 0, 0);
| ^
Edit:
compiler version
$ gcc --version
gcc (GCC) 11.3.1 20220421 (Red Hat 11.3.1-3)
This is because myfunc is a type, and need to declare a variable first.
typedef long (*myfunc)(long, long, long, long);
void mytest() {
myfunc abc = 0;
abc(0, 0, 0, 0);
}
What is needed:
Compile the json1 extension for SQLite
What I did:
Reaserched the official extension page: https://sqlite.org/loadext.html
Downloaded the SQLite source code: https://www.sqlite.org/cgi/src/doc/trunk/README.md
Found 2 ways to compile a dll:
cl windows command
gcc linux command
For the cl command I installed Visual Studio and launched the vcvars32.bat file for the enviroment launch, then tried this command: cl ext/misc/json1.c sqlite3ext.h /link /dll.
Docs: https://learn.microsoft.com/en-us/cpp/build/reference/compiler-command-line-syntax?view=vs-2019
However it didnt work and I got an error: fatal error C1083: sqlite3ext.h: No such file or directory.
I have the sqlite3ext.h file and tried moving it arround but nothing worked.
Then I moved to the gcc command:
I used the Ubuntu wsl
Upadated Ubuntu
Downloaded the source code (mensioned above)
Installed the SQLite developer package (can't find it)
Used this command: gcc -g -shared sqlite/ext/misc/json1.c -o json1.dll
Found the command on the SQLite extension page mensioned above
It didn't work and I got this long error message:
sqlite/ext/misc/json1.c: In function ‘jsonEachConnect’:
sqlite/ext/misc/json1.c:2099:29: error: ‘SQLITE_VTAB_INNOCUOUS’ undeclared (first use in this function); did you mean ‘SQLITE_STATIC’?
sqlite3_vtab_config(db, SQLITE_VTAB_INNOCUOUS);
^~~~~~~~~~~~~~~~~~~~~
SQLITE_STATIC
sqlite/ext/misc/json1.c:2099:29: note: each undeclared identifier is reported only once for each function it appears in
sqlite/ext/misc/json1.c: At top level:
sqlite/ext/misc/json1.c:2501:3: warning: excess elements in struct initializer
0 /* xShadowName */
^
sqlite/ext/misc/json1.c:2501:3: note: (near initialization for ‘jsonEachModule’)
sqlite/ext/misc/json1.c:2529:3: warning: excess elements in struct initializer
0 /* xShadowName */
^
sqlite/ext/misc/json1.c:2529:3: note: (near initialization for ‘jsonTreeModule’)
sqlite/ext/misc/json1.c: In function ‘sqlite3Json1Init’:
sqlite/ext/misc/json1.c:2594:8: error: ‘SQLITE_INNOCUOUS’ undeclared (first use in this function); did you mean ‘SQLITE_IGNORE’?
SQLITE_INNOCUOUS;
^~~~~~~~~~~~~~~~
SQLITE_IGNORE
sqlite/ext/misc/json1.c:2602:10: warning: implicit declaration of function ‘sqlite3_create_window_function’; did you mean ‘sqlite3_create_function’? [-Wimplicit-function-declaration]
rc = sqlite3_create_window_function(db, aAgg[i].zName, aAgg[i].nArg,
^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
sqlite3_create_function
sqlite/ext/misc/json1.c:2603:34: error: ‘SQLITE_SUBTYPE’ undeclared (first use in this function); did you mean ‘SQLITE_CANTOPEN’?
SQLITE_SUBTYPE | enc, 0,
^~~~~~~~~~~~~~
ANY HELP WOULD BE GREATLY APPRECIATED!
Thanks!
I had this problem with the SQLite UUID extension using "better-sqlite", but that's something else. What I did was replace everything that said SQLITE_INNOCUOUS and SQLITE_DETERMINISTIC with SQLITE_IGNORE. And it worked, at least for this extension. Something like the following:
Before:
{
int rc = SQLITE_OK;
SQLITE_EXTENSION_INIT2(pApi);
(void)pzErrMsg; /* Unused parameter */
rc = sqlite3_create_function(db, "uuid", 0, SQLITE_UTF8|SQLITE_INNOCUOUS, 0,
sqlite3UuidFunc, 0, 0);
if( rc==SQLITE_OK ){
rc = sqlite3_create_function(db, "uuid_str", 1,
SQLITE_UTF8|SQLITE_INNOCUOUS|SQLITE_DETERMINISTIC,
0, sqlite3UuidStrFunc, 0, 0);
}
if( rc==SQLITE_OK ){
rc = sqlite3_create_function(db, "uuid_blob", 1,
SQLITE_UTF8|SQLITE_INNOCUOUS|SQLITE_DETERMINISTIC,
0, sqlite3UuidBlobFunc, 0, 0);
}
return rc;
}
After:
{
int rc = SQLITE_OK;
SQLITE_EXTENSION_INIT2(pApi);
(void)pzErrMsg; /* Unused parameter */
rc = sqlite3_create_function(db, "uuid", 0, SQLITE_UTF8 | SQLITE_IGNORE, 0,
sqlite3UuidFunc, 0, 0);
if (rc == SQLITE_OK)
{
rc = sqlite3_create_function(db, "uuid_str", 1,
SQLITE_UTF8 | SQLITE_IGNORE | SQLITE_IGNORE,
0, sqlite3UuidStrFunc, 0, 0);
}
if (rc == SQLITE_OK)
{
rc = sqlite3_create_function(db, "uuid_blob", 1,
SQLITE_UTF8 | SQLITE_IGNORE | SQLITE_IGNORE,
0, sqlite3UuidBlobFunc, 0, 0);
}
return rc;
}
Edit
I just had to declare this at the beginning of the code.
#define SQLITE_DETERMINISTIC 0x000000800
#define SQLITE_DIRECTONLY 0x000080000
#define SQLITE_SUBTYPE 0x000100000
#define SQLITE_INNOCUOUS 0x000200000
I've been trying to get myself more acquainted with semaphores and was wondering why this code isn't printing the value I expect.
#include <semaphore.h>
#include <stdio.h>
#include <stdlib.h>
int main(int argc, char * argv[]) {
sem_t sem;
sem_init(&sem, 0, 1);
int value;
sem_getvalue(&sem, &value);
printf("%d\n",value);
return 0;
}
It prints 0 for the value. But from my understanding it should be getting the value I initialized the semaphore with which is 1? I tried using a semaphore in some code with pthreads and I initialized the semaphore with a value of 1, but when I called the sem_getvalue function it was printing 32767. Am I missing something here? Thanks in advance.
Edit: sem_init and sem_getvalue both return -1
Edit: Solved. It appears unnamed semaphores aren't implemented on Mac.
I'm getting the output as expected. (i.e. 1)
try using linking with pthread library
gcc sema.c -lpthread
Edit: Solved. It appears unnamed semaphores aren't implemented on Mac.
POSIX semaphore is considered as deprecated on Mac OSX. So, it doesn't work on it as expected.
It should return 1, which is the value you init,
when compile should add -pthread as option, e.g. gcc -pthread test.c
If the code runs well, then both sem_init() and sem_getvalue() should return 0,
if they return -1 then there is some error, you should get error flag, and check man page on linux to see what error happend.
By the way, your code return 1 on my linux, which is correct.
The man page: man sem_init and man sem_getvalue.
You should get error flag for sem_init(), then check man sem_init first, because the semaphore seems not properly created in the first place.
I have been coming across errors in compilation of my signal handler program written in C language with gcc in displaying the dumped register values after occurance of Segmentation fault. When i tried to access it using the code:
void print_registers(FILE *fd, ucontext_t *ctx, bool fpu = false)
{
const char *flags_str[] = {
"CF", 0, "PF", 0, "AF", 0, "ZF", "SF", "TP", "IF", "DF",
"OF", 0, 0, "NT", 0, "RF", "VM", "AC", "VIF", "VIP", "ID"
};
greg_t *regs = ctx->uc_mcontext.gregs;
void *eip[1] = { (void*)regs[REG_EIP] };
char **symbol = backtrace_symbols(eip, 1);
fprintf(fd, "Registers:\neip is at ");
backtrace_symbols_fd(eip, 1, fd->_fileno);
size_type flags = regs[REG_EFL];
fprintf(fd, "eflags: %x [ ", flags);
for (size_type i = 0; i < sizeof(flags_str) / sizeof(flags_str[0]); ++i) {
if (!flags_str[i]) continue;
if (flags & (1 << i)) fprintf(fd, "%s ", flags_str[i]);
}
size_type iopl = (flags & 0x3000) >> 12;
fprintf(fd, "] iopl: %i\n"
"eax: %08x\tebx: %08x\tecx: %08x\tedx: %08x\n"
"esi: %08x\tedi: %08x\tebp: %08x\tesp: %08x\n"
"cs: %04x\tgs: %04x\tfs: %04x\n"
"ds: %04x\tes: %04x\tss: %04x\n",
iopl,
regs[REG_EAX], regs[REG_EBX], regs[REG_ECX], regs[REG_EDX],
regs[REG_ESI], regs[REG_EDI], regs[REG_EBP], regs[REG_ESP],
regs[REG_CS], regs[REG_GS], regs[REG_FS],
regs[REG_DS], regs[REG_ES], regs[REG_SS]);
}
}
I tried the code by adding
#include<sys/ucontext.h>
as well as
#define _GNU_SOURCE
#ifndef REG_EIP
#define REG_EIP 0x23b46F
#endif
But, the error appearing is:
‘REG_EIP’ undeclared (first use in this function)
(Each undeclared identifier is reported only once for each function it appears in.)
and the error is appearing for all registers
I tried many documents...but couldn't get the solution.
Can anybody share the details for resolving this error.
Advance thanks to all repliers
I believe you should either have #define _GNU_SOURCE as the first line of your source file, or better put -D_GNU_SOURCE in your CFLAGS (on the command line). Then make sure you include <signal.h> and <ucontext.h>.
Try defining __USE_GNU before including <ucontext.h:
#define __USE_GNU
#include <ucontext.h>
You don't need to include <sys/ucontext.h> explicitly, <ucontext.h> will do that.
Try using 32 bit as those are 32 bit mode values. gcc -m32 should solve this.
For me, this was resolved with:
yum remove openssl-devel.x86_64
yum install openssl-devel.i686
on CentOS 6.4 (x86_64)
Hope this helps.
I am getting a crash when trying to use initstate_r:
(gdb) run
Starting program: /home/user/test.out
Program received signal SIGSEGV, Segmentation fault.
0x40052d00 in initstate_r () from /lib/libc.so.6
The code:
#include <stddef.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#define STATELEN 256 /* random number state buffer */
main()
{
char randomStateBuffer[STATELEN];
struct random_data randData;
printf("Before initstate");
/* seed the random number generator */
initstate_r (time(NULL), (char *)&randomStateBuffer, STATELEN,
(struct random_data *)&randData);
printf("initstate done");
}
I have tried compiling this in both gcc 3.3.6 and 4.3.3 and both have the crash.
Try zeroing out randData struct before calling initstate_r().
memset( &randData, 0, sizeof( random_data ) );
(Taking a cue from this page: http://sourceware.org/bugzilla/show_bug.cgi?id=3662)
This question looks amazingly similar to:
http://www.linuxquestions.org/questions/programming-9/crash-in-initstate_r-408757/
Also, see:
http://lists.debian.org/debian-glibc/2006/01/msg00037.html
and:
http://lists.debian.org/debian-glibc/2005/08/msg00492.html
The man page for that function is hard to understand, but it seems maybe rand_data should be initialized before passing to initstate_r
Looking at the function signature the second argument is just a char*. Take the address-of operator off randomStateBuffer.
initstate_r (time(NULL), randomStateBuffer, STATELEN,
(struct random_data *)&randData);
?
I've experienced the same difficulties and it worked by 0-ing out both state and rand_data, and in your case, removing the & in front of the buffer:
char randomStateBuffer[STATELEN];
struct random_data randData;
memset(randomStateBuffer, 0, sizeof(randomStateBuffer));
memset(&randData, 0, sizeof(struct random_data));
initstate_r(time(NULL), randomStateBuffer,sizeof(randomStateBuffer), &randData);
worked for me.