struct accessible without declaration? - c

I have the following Code
#ifdef ENV_TI
typedef struct timespecT
{
Uint32 tv_sec;
Uint32 tv_nsec;
}timespec;
#endif
#ifndef ENV_TI
struct timespec currentTime; // This Line
#else
timespec currentTime;
#endif
How is the currentTime accessible if i have NOT defined ENV_TI flag and the timespec is defined under the ENV_TI flag?
I am running this code on Linux, gcc compiler.

struct timespec is a type name used in e.g. Linux, see the manual page for clock_gettime(). You get the type declaration by doing #include <time.h> on systems that support it. According to the manual page, this is POSIX standard functionality.
I think the code you're looking at is using the #ifdef to declare the type for environments that don't support it natively.

timespec is also the name of a struct defined in time.h

Related

error: dereferencing pointer to incomplete type on stub of gettimeofday

Haven't done much c programming and am running into "error: dereferencing pointer to incomplete type".
Attempting to stub out gettimeofday with call to clock_gettime.
Here is code
#include <time.h>
int gettimeofday(struct timeval *tv, struct timezone *tz)
/* This procedure stubs out call to gettimeofday */
{
struct timespec spec;
// initialize result status to invalid
int result = -1;
// if passed in pointer tv is not NULL
if (tv) {
// retrieve time
result = clock_gettime(CLOCK_REALTIME, &spec);
// if time retreived is valid then
if (result == 0){
tv->tv_sec = spec.tv_sec; // seconds
tv->tv_usec = (spec.tv_nsec / 1.0e3); // Convert nanoseconds to microseconds
}
}
return result;
}
I get the "error dereferencing pointer to incomplete type" on assignment
tv->tv_sec = spec.tv_sec; // seconds
If I compile/link in linux target=i686-pc-linux-gnu but no error intarget=powerpc-xcoff-lynxos178 target environment.
I am #include and that has definition timespec
time.h is different for each target. Thank you for taking time to look at this.
Along with the need for #include <sys/time.h> you are probably seeing a conflict with the prototype for the system's gettimeofday() call. On many systems the second parameter is void *.
The issue for this stub of gettimeofday was we were trying to write the stub to work in 3 different environments. Windows, Linux target and powerpc target - each of which seems to have slight variants in OS headers. What we ended up doing was adding a compiler directive to handle linux vs the other environments where we did not have issues. This is ultimately what we went with - I thought we should have avoided the stub and just called clock_gettime but there were reasons why this way was cheaper.
#include <time.h>
#include <sys/time.h>
#ifdef __linux__
int gettimeofday(struct timeval *__restrict __tv, __timezone_ptr_t __tz)
#else
int gettimeofday(struct timeval * __tv, struct timezone* __tz)
#endif

Timespec redefinition error [duplicate]

This question already has answers here:
Visual Studio error with 'timespec' structure
(5 answers)
Closed 6 years ago.
While executing a Pthread program in C using Visual Studio 2015, I got the following error:
Error C2011 'timespec': 'struct' type redefinition
The following is my code:
#include<pthread.h>
#include<stdlib.h>
#include<stdio.h>
void *calculator(void *parameter);
int main(/*int *argc,char *argv[]*/)
{
pthread_t thread_obj;
pthread_attr_t thread_attr;
char *First_string = "abc"/*argv[1]*/;
pthread_attr_init(&thread_attr);
pthread_create(&thread_obj,&thread_attr,calculator,First_string);
}
void *calculator(void *parameter)
{
int x=atoi((char*)parameter);
printf("x=%d", x);
}
The pthread.h header file contains the following code related to timespec:
#if !defined(HAVE_STRUCT_TIMESPEC)
#define HAVE_STRUCT_TIMESPEC
#if !defined(_TIMESPEC_DEFINED)
#define _TIMESPEC_DEFINED
struct timespec {
time_t tv_sec;
long tv_nsec;
};
#endif /* _TIMESPEC_DEFINED */
#endif /* HAVE_STRUCT_TIMESPEC */
No other header file which I use uses the timespec struct, so there is no chance of redefining. There is no chance of a corrupted header file because it has been downloaded from pthread opensource website.
pthreads-win32 (which I assume you're using) may internally include time.h (time.h is also commonly included by other libraries/headers) - and time.h already declares timespec (also, it does so in a way compatible with pthreads) - yet the pthreads-win32's pthread.h doesn't have the valid include guards for this case (shame on them!). pthreads tries to declare it because it needs it internally, but since it's possible it won't need the entire time.h, it tries to declare only the timespec if possible. Still, you can simply add
#define HAVE_STRUCT_TIMESPEC
before #include <pthread.h> - that will tell the pthreads-win32 header that you already have a proper timespec, and will let your code compile properly.
Alternatively, if you're using pthreads extensively, you may wish to edit the header file itself - simply add that #define HAVE_STRUCT_TIMESPEC to it somewhere near the beginning, and you're good to go.
Further reading: http://mingw-users.1079350.n2.nabble.com/mingw-error-redefinition-of-struct-timespec-td7583722.html

Time structure in linux mint

I'm newbie in C/Linux and I've one simple question. Consider the sys/timerfd.h header file. It consist the function definition:
int timerfd_settime(int fd, int flags,
const struct itimerspec *new_value,
struct itimerspec *old_value);
I can't find the struct itimerspec declaration in the sys/timerfd.h. Where is this structure declared. I'm looking for header file.
man (7) time.h
The header shall also declare the itimerspec structure, which has at least the following members:
struct timespec it_interval Timer period.
struct timespec it_value Timer expiration.
It's usually sys/time.h too.

resolving redefinition of timespec in time.h

I am writing a program which includes both /usr/include/linux/time.h and /usr/include/stdlib.h.
The problem is:
stdlib.h includes /usr/include/time.h, which defines 'struct timespec', and /usr/include/linux/time.h also defines one. This introduces a compilation error of redefinition.
I've examined the definitions of 'struct timespec' in these two header files:
in /usr/include/time.h:
struct timespec
{
__time_t tv_sec; /* Seconds. */
long int tv_nsec; /* Nanoseconds. */
};
in /usr/include/linux/time.h:
struct timespec {
__kernel_time_t tv_sec; /* seconds */
long tv_nsec; /* nanoseconds */
};
It seems that these definitions are indeed equivalent, but I can't prove it.
My question is: is there a robust way to resolve this redefinition?
Links to discussions on this problem are also highly appreciated. Thanks.
One way to resolve the double-definition error is to rename one of these definitions:
#include <time.h>
#define timespec linux_timespec
#include <linux/time.h>
#undef timespec
And then assert at compile time that both definitions have the same layout:
typedef int assert_same_size[sizeof(struct linux_timespec) == sizeof(timespec) ? 1 : -1];
typedef int assert_same_alignment[__alignof(struct linux_timespec) == __alignof(timespec) ? 1 : -1];
typedef int assert_same_tv_sec[offsetof(struct linux_timespec, tv_sec) == offsetof(struct timespec, tv_sec) ? 1 : -1];
typedef int assert_same_tv_nsec[offsetof(struct linux_timespec, tv_nsec) == offsetof(struct timespec, tv_nsec) ? 1 : -1];
I got the same error in Ecliepse Neon IDE and i resolved it by adding -DHAVE_STRUCT_TIMESPEC in C/C++ Build -> Settings -> GCC C++ Compiler -> Miscellaneous -> Others flag

Any specific reason why localtime throws warning with struct tm* & stat* , in linux ?

I have this simple code (part of a project) :
void displayFileProperties(struct stat* file,char* outputProperties , char * path)
{
struct tm* time;
// code
// code
time = localtime(&file->st_mtim);
// code
}
Where eclipse keeps throwing me a warning :
passing argument 1 of ‘localtime’ from incompatible pointer type [enabled by default] main.c /ex4 line 340 C/C++ Problem
Any idea how to fix this ? thanks
st_mtim is a struct timespec (seconds and nanoseconds). You want st_mtime.
You'll want to use this instead:
time = localtime(&file->st_mtime);
Note the added 'e' at the end. st_mtim is a timespec, with 'e' added it's a time_t (what you need).
Completely changed answer:
SUGGESTIONS:
1) Make sure you #include these headers:
#include <time.h>
#include <sys/types.h>
#include <sys/stat.h>
2) Cast your pointer to "const"
time = localtime((const time_t *)&file->st_mtime);
3) Post back what happens
=====================================================
ADDITIONAL SUGGESTIONS:
1) Please read these two links:
C stat struct does not have st_ctime field but only st_ctim
http://linux.die.net/man/2/lstat
Since kernel 2.5.48, the stat structure supports nanosecond resolution
for the three file timestamp fields. Glibc exposes the nanosecond
component of each field using names of the form st_atim.tv_nsec if the
_BSD_SOURCE or _SVID_SOURCE feature test macro is defined. These fields are specified in POSIX.1-2008, and, starting with version 2.12,
glibc also exposes these field names if _POSIX_C_SOURCE is defined
with the value 200809L or greater, or _XOPEN_SOURCE is defined with
the value 700 or greater. If none of the aforementioned macros are
defined, then the nanosecond values are exposed with names of the form
st_atimensec. On file systems that do not support subsecond
timestamps, the nanosecond fields are returned with the value 0.
2) Clearly, the makefile (that "works") has a #define that Eclipse doesn't, or vice versa.
Probably either/both _POSIX_C_SOURCE and/or _XOPEN_SOURCE.
Run this command to see what exists in the command line (makefile?) environment:
gcc -dM -E - < /dev/null | less
3) Please post back what you find!
I had the same issue with Eclipse:
Field st_mtime could not be resolved (semantic error)
Fixed the issue in Eclipse by right-clicking the project, choose Index->"Freshen All Files"
#include <malloc.h>
#include <time.h>
#include <stdio.h>
static struct tm* alarmTime(void);
int main(){
printf("Hour :%i\n", alarmTime()->tm_hour);
printf("Minute :%i\n", alarmTime()->tm_min);
return 0;
}
static struct tm* alarmTime(void){
time_t now = time(NULL);
struct tm* ptm;
#ifdef HAVE_LOCALTIME_R
struct tm tmbuf;
ptm = localtime_r(&now, &tmbuf);
#else
ptm = localtime(&now);
#endif
return ptm;
}

Resources