Add emulated serialIo device driver for EdkUnixPkg
[mirror_edk2.git] / EdkUnixPkg / Sec / UnixThunk.c
CommitLineData
c9093a06 1/*++\r
2\r
3Copyright (c) 2004 - 2006, Intel Corporation \r
4All rights reserved. This program and the accompanying materials \r
5are licensed and made available under the terms and conditions of the BSD License \r
6which accompanies this distribution. The full text of the license may be found at \r
7http://opensource.org/licenses/bsd-license.php \r
8 \r
9THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, \r
10WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. \r
11\r
12Module Name:\r
13\r
14 UnixThunk.c\r
15\r
16Abstract:\r
17\r
18 Since the SEC is the only program in our emulation we \r
19 must use a Tiano mechanism to export APIs to other modules.\r
20 This is the role of the EFI_UNIX_THUNK_PROTOCOL.\r
21\r
22 The mUnixThunkTable exists so that a change to EFI_UNIX_THUNK_PROTOCOL\r
23 will cause an error in initializing the array if all the member functions\r
24 are not added. It looks like adding a element to end and not initializing\r
25 it may cause the table to be initaliized with the members at the end being\r
26 set to zero. This is bad as jumping to zero will crash.\r
27 \r
28\r
29 gUnix is a a public exported global that contains the initialized\r
30 data.\r
31\r
32--*/\r
33\r
34#include "SecMain.h"\r
35#include "Library/UnixLib.h"
36#include <sys/time.h>
37#include <time.h>
38#include <signal.h>
39#include <string.h>
b19cfa69 40#include <stdlib.h>\r
41#include <termio.h>
c9093a06 42
43static int settimer_initialized;
44static struct timeval settimer_timeval;
45static void (*settimer_callback)(UINT64 delta);
46
47static void
48settimer_handler (int sig)
49{
50 struct timeval timeval;
51 UINT64 delta;
52
53 gettimeofday (&timeval, NULL);
54 delta = ((UINT64)timeval.tv_sec * 1000) + (timeval.tv_usec / 1000)
55 - ((UINT64)settimer_timeval.tv_sec * 1000)
56 - (settimer_timeval.tv_usec / 1000);
57 settimer_timeval = timeval;
58 if (settimer_callback)
59 (*settimer_callback)(delta);
60}
61
62static
63VOID
64SetTimer (UINT64 PeriodMs, VOID (*CallBack)(UINT64 DeltaMs))
65{
66 struct itimerval timerval;
67
68 if (!settimer_initialized) {
69 struct sigaction act;
70
71 settimer_initialized = 1;
72 act.sa_handler = settimer_handler;
73 act.sa_flags = 0;
74 sigemptyset (&act.sa_mask);
75 if (sigaction (SIGALRM, &act, NULL) != 0) {
76 printf ("SetTimer: sigaction error %s\n", strerror (errno));
77 }
78 if (gettimeofday (&settimer_timeval, NULL) != 0) {
79 printf ("SetTimer: gettimeofday error %s\n", strerror (errno));
80 }
81 }
82 timerval.it_value.tv_sec = PeriodMs / 1000;
83 timerval.it_value.tv_usec = (PeriodMs % 1000) * 1000;
84 timerval.it_value.tv_sec = PeriodMs / 1000;
85 timerval.it_interval = timerval.it_value;
86
87 if (setitimer (ITIMER_REAL, &timerval, NULL) != 0) {
88 printf ("SetTimer: setitimer error %s\n", strerror (errno));
89 }
90 settimer_callback = CallBack;
91}
92
8ba2f441 93void
94msSleep (unsigned long Milliseconds)
95{
96 struct timespec ts;
97
98 ts.tv_sec = Milliseconds / 1000;
99 ts.tv_nsec = (Milliseconds % 1000) * 1000000;
100
101 while (nanosleep (&ts, &ts) != 0 && errno == EINTR)
102 ;
103}
104
c9093a06 105void
106GetLocalTime (EFI_TIME *Time)
107{
108 struct tm *tm;
109 time_t t;
110
111 t = time (NULL);
112 tm = localtime (&t);
113
114 Time->Year = 1900 + tm->tm_year;
115 Time->Month = tm->tm_mon;
116 Time->Day = tm->tm_mday;
117 Time->Hour = tm->tm_hour;
118 Time->Minute = tm->tm_min;
119 Time->Second = tm->tm_sec;
120 Time->Nanosecond = 0;
121 Time->TimeZone = timezone;
122 Time->Daylight = (daylight ? EFI_TIME_ADJUST_DAYLIGHT : 0)
123 | (tm->tm_isdst > 0 ? EFI_TIME_IN_DAYLIGHT : 0);
124}
125
c9093a06 126static void
127TzSet (void)
128{
129 static int done = 0;
130 if (!done) {
131 tzset ();
132 done = 1;
133 }
134}
135
136long
137GetTimeZone(void)
138{
139 TzSet ();
140 return timezone;
141}
142
143int
144GetDayLight(void)
145{
146 TzSet ();
147 return daylight;
148}
149
150int
151GetErrno(void)
152{
153 return errno;
154}
155
156extern EFI_STATUS
8ef571df 157UgaCreate(struct _EFI_UNIX_UGA_IO_PROTOCOL **UgaIo, CONST CHAR16 *Title);
c9093a06 158
159EFI_UNIX_THUNK_PROTOCOL mUnixThunkTable = {\r
160 EFI_UNIX_THUNK_PROTOCOL_SIGNATURE,\r
161 msSleep, /* Sleep */
162 exit, /* Exit */
163 SetTimer,
164 GetLocalTime,
165 gmtime,
166 GetTimeZone,
167 GetDayLight,
168 (UnixPoll)poll,
169 (UnixRead)read,
170 (UnixWrite)write,
171 getenv,
172 (UnixOpen)open,
173 lseek,
174 ftruncate,
175 close,
176 mkdir,
177 rmdir,
178 unlink,
179 GetErrno,
180 opendir,
181 rewinddir,
182 readdir,
183 closedir,
184 stat,
185 statfs,
186 rename,
187 mktime,
188 fsync,
189 chmod,
190 utime,
b19cfa69 191 tcflush,
192 UgaCreate,\r
193 perror,\r
194 printf,\r
195 ioctl,\r
196 fcntl,\r
197 cfsetispeed,\r
198 cfsetospeed,\r
199 tcgetattr,\r
200 tcsetattr
c9093a06 201};\r
202\r
203\r
204EFI_UNIX_THUNK_PROTOCOL *gUnix = &mUnixThunkTable;\r