]> CyberLeo.Net >> Repos - FreeBSD/stable/10.git/blob - sys/contrib/dev/acpica/os_specific/service_layers/osunixxf.c
Copy head (r256279) to stable/10 as part of the 10.0-RELEASE cycle.
[FreeBSD/stable/10.git] / sys / contrib / dev / acpica / os_specific / service_layers / osunixxf.c
1 /******************************************************************************
2  *
3  * Module Name: osunixxf - UNIX OSL interfaces
4  *
5  *****************************************************************************/
6
7 /*
8  * Copyright (C) 2000 - 2013, Intel Corp.
9  * All rights reserved.
10  *
11  * Redistribution and use in source and binary forms, with or without
12  * modification, are permitted provided that the following conditions
13  * are met:
14  * 1. Redistributions of source code must retain the above copyright
15  *    notice, this list of conditions, and the following disclaimer,
16  *    without modification.
17  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
18  *    substantially similar to the "NO WARRANTY" disclaimer below
19  *    ("Disclaimer") and any redistribution must be conditioned upon
20  *    including a substantially similar Disclaimer requirement for further
21  *    binary redistribution.
22  * 3. Neither the names of the above-listed copyright holders nor the names
23  *    of any contributors may be used to endorse or promote products derived
24  *    from this software without specific prior written permission.
25  *
26  * Alternatively, this software may be distributed under the terms of the
27  * GNU General Public License ("GPL") version 2 as published by the Free
28  * Software Foundation.
29  *
30  * NO WARRANTY
31  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
32  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
33  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
34  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
35  * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
36  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
37  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
38  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
39  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
40  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
41  * POSSIBILITY OF SUCH DAMAGES.
42  */
43
44
45 /*
46  * These interfaces are required in order to compile the ASL compiler and the
47  * various ACPICA tools under Linux or other Unix-like system.
48  */
49 #include <contrib/dev/acpica/include/acpi.h>
50 #include <contrib/dev/acpica/include/accommon.h>
51 #include <contrib/dev/acpica/include/amlcode.h>
52 #include <contrib/dev/acpica/include/acparser.h>
53 #include <contrib/dev/acpica/include/acdebug.h>
54
55 #include <stdio.h>
56 #include <stdlib.h>
57 #include <stdarg.h>
58 #include <unistd.h>
59 #include <sys/time.h>
60 #include <semaphore.h>
61 #include <pthread.h>
62 #include <errno.h>
63
64 #define _COMPONENT          ACPI_OS_SERVICES
65         ACPI_MODULE_NAME    ("osunixxf")
66
67
68 extern FILE                    *AcpiGbl_DebugFile;
69 FILE                           *AcpiGbl_OutputFile;
70
71
72 /* Upcalls to AcpiExec */
73
74 ACPI_PHYSICAL_ADDRESS
75 AeLocalGetRootPointer (
76     void);
77
78 void
79 AeTableOverride (
80     ACPI_TABLE_HEADER       *ExistingTable,
81     ACPI_TABLE_HEADER       **NewTable);
82
83 typedef void* (*PTHREAD_CALLBACK) (void *);
84
85 /* Buffer used by AcpiOsVprintf */
86
87 #define ACPI_VPRINTF_BUFFER_SIZE        512
88
89
90 /******************************************************************************
91  *
92  * FUNCTION:    AcpiOsInitialize, AcpiOsTerminate
93  *
94  * PARAMETERS:  None
95  *
96  * RETURN:      Status
97  *
98  * DESCRIPTION: Init and terminate. Nothing to do.
99  *
100  *****************************************************************************/
101
102 ACPI_STATUS
103 AcpiOsInitialize (
104     void)
105 {
106
107     AcpiGbl_OutputFile = stdout;
108     return (AE_OK);
109 }
110
111
112 ACPI_STATUS
113 AcpiOsTerminate (
114     void)
115 {
116
117     return (AE_OK);
118 }
119
120
121 /******************************************************************************
122  *
123  * FUNCTION:    AcpiOsGetRootPointer
124  *
125  * PARAMETERS:  None
126  *
127  * RETURN:      RSDP physical address
128  *
129  * DESCRIPTION: Gets the ACPI root pointer (RSDP)
130  *
131  *****************************************************************************/
132
133 ACPI_PHYSICAL_ADDRESS
134 AcpiOsGetRootPointer (
135     void)
136 {
137
138     return (AeLocalGetRootPointer ());
139 }
140
141
142 /******************************************************************************
143  *
144  * FUNCTION:    AcpiOsPredefinedOverride
145  *
146  * PARAMETERS:  InitVal             - Initial value of the predefined object
147  *              NewVal              - The new value for the object
148  *
149  * RETURN:      Status, pointer to value. Null pointer returned if not
150  *              overriding.
151  *
152  * DESCRIPTION: Allow the OS to override predefined names
153  *
154  *****************************************************************************/
155
156 ACPI_STATUS
157 AcpiOsPredefinedOverride (
158     const ACPI_PREDEFINED_NAMES *InitVal,
159     ACPI_STRING                 *NewVal)
160 {
161
162     if (!InitVal || !NewVal)
163     {
164         return (AE_BAD_PARAMETER);
165     }
166
167     *NewVal = NULL;
168     return (AE_OK);
169 }
170
171
172 /******************************************************************************
173  *
174  * FUNCTION:    AcpiOsTableOverride
175  *
176  * PARAMETERS:  ExistingTable       - Header of current table (probably
177  *                                    firmware)
178  *              NewTable            - Where an entire new table is returned.
179  *
180  * RETURN:      Status, pointer to new table. Null pointer returned if no
181  *              table is available to override
182  *
183  * DESCRIPTION: Return a different version of a table if one is available
184  *
185  *****************************************************************************/
186
187 ACPI_STATUS
188 AcpiOsTableOverride (
189     ACPI_TABLE_HEADER       *ExistingTable,
190     ACPI_TABLE_HEADER       **NewTable)
191 {
192
193     if (!ExistingTable || !NewTable)
194     {
195         return (AE_BAD_PARAMETER);
196     }
197
198     *NewTable = NULL;
199
200 #ifdef ACPI_EXEC_APP
201
202     AeTableOverride (ExistingTable, NewTable);
203     return (AE_OK);
204 #else
205
206     return (AE_NO_ACPI_TABLES);
207 #endif
208 }
209
210
211 /******************************************************************************
212  *
213  * FUNCTION:    AcpiOsPhysicalTableOverride
214  *
215  * PARAMETERS:  ExistingTable       - Header of current table (probably firmware)
216  *              NewAddress          - Where new table address is returned
217  *                                    (Physical address)
218  *              NewTableLength      - Where new table length is returned
219  *
220  * RETURN:      Status, address/length of new table. Null pointer returned
221  *              if no table is available to override.
222  *
223  * DESCRIPTION: Returns AE_SUPPORT, function not used in user space.
224  *
225  *****************************************************************************/
226
227 ACPI_STATUS
228 AcpiOsPhysicalTableOverride (
229     ACPI_TABLE_HEADER       *ExistingTable,
230     ACPI_PHYSICAL_ADDRESS   *NewAddress,
231     UINT32                  *NewTableLength)
232 {
233
234     return (AE_SUPPORT);
235 }
236
237
238 /******************************************************************************
239  *
240  * FUNCTION:    AcpiOsRedirectOutput
241  *
242  * PARAMETERS:  Destination         - An open file handle/pointer
243  *
244  * RETURN:      None
245  *
246  * DESCRIPTION: Causes redirect of AcpiOsPrintf and AcpiOsVprintf
247  *
248  *****************************************************************************/
249
250 void
251 AcpiOsRedirectOutput (
252     void                    *Destination)
253 {
254
255     AcpiGbl_OutputFile = Destination;
256 }
257
258
259 /******************************************************************************
260  *
261  * FUNCTION:    AcpiOsPrintf
262  *
263  * PARAMETERS:  fmt, ...            - Standard printf format
264  *
265  * RETURN:      None
266  *
267  * DESCRIPTION: Formatted output. Note: very similar to AcpiOsVprintf
268  *              (performance), changes should be tracked in both functions.
269  *
270  *****************************************************************************/
271
272 void ACPI_INTERNAL_VAR_XFACE
273 AcpiOsPrintf (
274     const char              *Fmt,
275     ...)
276 {
277     va_list                 Args;
278     UINT8                   Flags;
279
280
281     Flags = AcpiGbl_DbOutputFlags;
282     if (Flags & ACPI_DB_REDIRECTABLE_OUTPUT)
283     {
284         /* Output is directable to either a file (if open) or the console */
285
286         if (AcpiGbl_DebugFile)
287         {
288             /* Output file is open, send the output there */
289
290             va_start (Args, Fmt);
291             vfprintf (AcpiGbl_DebugFile, Fmt, Args);
292             va_end (Args);
293         }
294         else
295         {
296             /* No redirection, send output to console (once only!) */
297
298             Flags |= ACPI_DB_CONSOLE_OUTPUT;
299         }
300     }
301
302     if (Flags & ACPI_DB_CONSOLE_OUTPUT)
303     {
304         va_start (Args, Fmt);
305         vfprintf (AcpiGbl_OutputFile, Fmt, Args);
306         va_end (Args);
307     }
308 }
309
310
311 /******************************************************************************
312  *
313  * FUNCTION:    AcpiOsVprintf
314  *
315  * PARAMETERS:  fmt                 - Standard printf format
316  *              args                - Argument list
317  *
318  * RETURN:      None
319  *
320  * DESCRIPTION: Formatted output with argument list pointer. Note: very
321  *              similar to AcpiOsPrintf, changes should be tracked in both
322  *              functions.
323  *
324  *****************************************************************************/
325
326 void
327 AcpiOsVprintf (
328     const char              *Fmt,
329     va_list                 Args)
330 {
331     UINT8                   Flags;
332     char                    Buffer[ACPI_VPRINTF_BUFFER_SIZE];
333
334
335     /*
336      * We build the output string in a local buffer because we may be
337      * outputting the buffer twice. Using vfprintf is problematic because
338      * some implementations modify the args pointer/structure during
339      * execution. Thus, we use the local buffer for portability.
340      *
341      * Note: Since this module is intended for use by the various ACPICA
342      * utilities/applications, we can safely declare the buffer on the stack.
343      * Also, This function is used for relatively small error messages only.
344      */
345     vsnprintf (Buffer, ACPI_VPRINTF_BUFFER_SIZE, Fmt, Args);
346
347     Flags = AcpiGbl_DbOutputFlags;
348     if (Flags & ACPI_DB_REDIRECTABLE_OUTPUT)
349     {
350         /* Output is directable to either a file (if open) or the console */
351
352         if (AcpiGbl_DebugFile)
353         {
354             /* Output file is open, send the output there */
355
356             fputs (Buffer, AcpiGbl_DebugFile);
357         }
358         else
359         {
360             /* No redirection, send output to console (once only!) */
361
362             Flags |= ACPI_DB_CONSOLE_OUTPUT;
363         }
364     }
365
366     if (Flags & ACPI_DB_CONSOLE_OUTPUT)
367     {
368         fputs (Buffer, AcpiGbl_OutputFile);
369     }
370 }
371
372
373 /******************************************************************************
374  *
375  * FUNCTION:    AcpiOsGetLine
376  *
377  * PARAMETERS:  Buffer              - Where to return the command line
378  *              BufferLength        - Maximum length of Buffer
379  *              BytesRead           - Where the actual byte count is returned
380  *
381  * RETURN:      Status and actual bytes read
382  *
383  * DESCRIPTION: Formatted input with argument list pointer
384  *
385  *****************************************************************************/
386
387 ACPI_STATUS
388 AcpiOsGetLine (
389     char                    *Buffer,
390     UINT32                  BufferLength,
391     UINT32                  *BytesRead)
392 {
393     int                     Temp;
394     UINT32                  i;
395
396
397     for (i = 0; ; i++)
398     {
399         if (i >= BufferLength)
400         {
401             return (AE_BUFFER_OVERFLOW);
402         }
403
404         if ((Temp = getchar ()) == EOF)
405         {
406             return (AE_ERROR);
407         }
408
409         if (!Temp || Temp == '\n')
410         {
411             break;
412         }
413
414         Buffer [i] = (char) Temp;
415     }
416
417     /* Null terminate the buffer */
418
419     Buffer [i] = 0;
420
421     /* Return the number of bytes in the string */
422
423     if (BytesRead)
424     {
425         *BytesRead = i;
426     }
427     return (AE_OK);
428 }
429
430
431 /******************************************************************************
432  *
433  * FUNCTION:    AcpiOsMapMemory
434  *
435  * PARAMETERS:  where               - Physical address of memory to be mapped
436  *              length              - How much memory to map
437  *
438  * RETURN:      Pointer to mapped memory. Null on error.
439  *
440  * DESCRIPTION: Map physical memory into caller's address space
441  *
442  *****************************************************************************/
443
444 void *
445 AcpiOsMapMemory (
446     ACPI_PHYSICAL_ADDRESS   where,
447     ACPI_SIZE               length)
448 {
449
450     return (ACPI_TO_POINTER ((ACPI_SIZE) where));
451 }
452
453
454 /******************************************************************************
455  *
456  * FUNCTION:    AcpiOsUnmapMemory
457  *
458  * PARAMETERS:  where               - Logical address of memory to be unmapped
459  *              length              - How much memory to unmap
460  *
461  * RETURN:      None.
462  *
463  * DESCRIPTION: Delete a previously created mapping. Where and Length must
464  *              correspond to a previous mapping exactly.
465  *
466  *****************************************************************************/
467
468 void
469 AcpiOsUnmapMemory (
470     void                    *where,
471     ACPI_SIZE               length)
472 {
473
474     return;
475 }
476
477
478 /******************************************************************************
479  *
480  * FUNCTION:    AcpiOsAllocate
481  *
482  * PARAMETERS:  Size                - Amount to allocate, in bytes
483  *
484  * RETURN:      Pointer to the new allocation. Null on error.
485  *
486  * DESCRIPTION: Allocate memory. Algorithm is dependent on the OS.
487  *
488  *****************************************************************************/
489
490 void *
491 AcpiOsAllocate (
492     ACPI_SIZE               size)
493 {
494     void                    *Mem;
495
496
497     Mem = (void *) malloc ((size_t) size);
498     return (Mem);
499 }
500
501
502 /******************************************************************************
503  *
504  * FUNCTION:    AcpiOsFree
505  *
506  * PARAMETERS:  mem                 - Pointer to previously allocated memory
507  *
508  * RETURN:      None.
509  *
510  * DESCRIPTION: Free memory allocated via AcpiOsAllocate
511  *
512  *****************************************************************************/
513
514 void
515 AcpiOsFree (
516     void                    *mem)
517 {
518
519     free (mem);
520 }
521
522
523 #ifdef ACPI_SINGLE_THREADED
524 /******************************************************************************
525  *
526  * FUNCTION:    Semaphore stub functions
527  *
528  * DESCRIPTION: Stub functions used for single-thread applications that do
529  *              not require semaphore synchronization. Full implementations
530  *              of these functions appear after the stubs.
531  *
532  *****************************************************************************/
533
534 ACPI_STATUS
535 AcpiOsCreateSemaphore (
536     UINT32              MaxUnits,
537     UINT32              InitialUnits,
538     ACPI_HANDLE         *OutHandle)
539 {
540     *OutHandle = (ACPI_HANDLE) 1;
541     return (AE_OK);
542 }
543
544 ACPI_STATUS
545 AcpiOsDeleteSemaphore (
546     ACPI_HANDLE         Handle)
547 {
548     return (AE_OK);
549 }
550
551 ACPI_STATUS
552 AcpiOsWaitSemaphore (
553     ACPI_HANDLE         Handle,
554     UINT32              Units,
555     UINT16              Timeout)
556 {
557     return (AE_OK);
558 }
559
560 ACPI_STATUS
561 AcpiOsSignalSemaphore (
562     ACPI_HANDLE         Handle,
563     UINT32              Units)
564 {
565     return (AE_OK);
566 }
567
568 #else
569 /******************************************************************************
570  *
571  * FUNCTION:    AcpiOsCreateSemaphore
572  *
573  * PARAMETERS:  InitialUnits        - Units to be assigned to the new semaphore
574  *              OutHandle           - Where a handle will be returned
575  *
576  * RETURN:      Status
577  *
578  * DESCRIPTION: Create an OS semaphore
579  *
580  *****************************************************************************/
581
582 ACPI_STATUS
583 AcpiOsCreateSemaphore (
584     UINT32              MaxUnits,
585     UINT32              InitialUnits,
586     ACPI_HANDLE         *OutHandle)
587 {
588     sem_t               *Sem;
589
590
591     if (!OutHandle)
592     {
593         return (AE_BAD_PARAMETER);
594     }
595
596 #ifdef __APPLE__
597     {
598         char            *SemaphoreName = tmpnam (NULL);
599
600         Sem = sem_open (SemaphoreName, O_EXCL|O_CREAT, 0755, InitialUnits);
601         if (!Sem)
602         {
603             return (AE_NO_MEMORY);
604         }
605         sem_unlink (SemaphoreName); /* This just deletes the name */
606     }
607
608 #else
609     Sem = AcpiOsAllocate (sizeof (sem_t));
610     if (!Sem)
611     {
612         return (AE_NO_MEMORY);
613     }
614
615     if (sem_init (Sem, 0, InitialUnits) == -1)
616     {
617         AcpiOsFree (Sem);
618         return (AE_BAD_PARAMETER);
619     }
620 #endif
621
622     *OutHandle = (ACPI_HANDLE) Sem;
623     return (AE_OK);
624 }
625
626
627 /******************************************************************************
628  *
629  * FUNCTION:    AcpiOsDeleteSemaphore
630  *
631  * PARAMETERS:  Handle              - Handle returned by AcpiOsCreateSemaphore
632  *
633  * RETURN:      Status
634  *
635  * DESCRIPTION: Delete an OS semaphore
636  *
637  *****************************************************************************/
638
639 ACPI_STATUS
640 AcpiOsDeleteSemaphore (
641     ACPI_HANDLE         Handle)
642 {
643     sem_t               *Sem = (sem_t *) Handle;
644
645
646     if (!Sem)
647     {
648         return (AE_BAD_PARAMETER);
649     }
650
651     if (sem_destroy (Sem) == -1)
652     {
653         return (AE_BAD_PARAMETER);
654     }
655
656     return (AE_OK);
657 }
658
659
660 /******************************************************************************
661  *
662  * FUNCTION:    AcpiOsWaitSemaphore
663  *
664  * PARAMETERS:  Handle              - Handle returned by AcpiOsCreateSemaphore
665  *              Units               - How many units to wait for
666  *              MsecTimeout         - How long to wait (milliseconds)
667  *
668  * RETURN:      Status
669  *
670  * DESCRIPTION: Wait for units
671  *
672  *****************************************************************************/
673
674 ACPI_STATUS
675 AcpiOsWaitSemaphore (
676     ACPI_HANDLE         Handle,
677     UINT32              Units,
678     UINT16              MsecTimeout)
679 {
680     ACPI_STATUS         Status = AE_OK;
681     sem_t               *Sem = (sem_t *) Handle;
682 #ifndef ACPI_USE_ALTERNATE_TIMEOUT
683     struct timespec     Time;
684     int                 RetVal;
685 #endif
686
687
688     if (!Sem)
689     {
690         return (AE_BAD_PARAMETER);
691     }
692
693     switch (MsecTimeout)
694     {
695     /*
696      * No Wait:
697      * --------
698      * A zero timeout value indicates that we shouldn't wait - just
699      * acquire the semaphore if available otherwise return AE_TIME
700      * (a.k.a. 'would block').
701      */
702     case 0:
703
704         if (sem_trywait(Sem) == -1)
705         {
706             Status = (AE_TIME);
707         }
708         break;
709
710     /* Wait Indefinitely */
711
712     case ACPI_WAIT_FOREVER:
713
714         if (sem_wait (Sem))
715         {
716             Status = (AE_TIME);
717         }
718         break;
719
720     /* Wait with MsecTimeout */
721
722     default:
723
724 #ifdef ACPI_USE_ALTERNATE_TIMEOUT
725         /*
726          * Alternate timeout mechanism for environments where
727          * sem_timedwait is not available or does not work properly.
728          */
729         while (MsecTimeout)
730         {
731             if (sem_trywait (Sem) == 0)
732             {
733                 /* Got the semaphore */
734                 return (AE_OK);
735             }
736
737             if (MsecTimeout >= 10)
738             {
739                 MsecTimeout -= 10;
740                 usleep (10 * ACPI_USEC_PER_MSEC); /* ten milliseconds */
741             }
742             else
743             {
744                 MsecTimeout--;
745                 usleep (ACPI_USEC_PER_MSEC); /* one millisecond */
746             }
747         }
748         Status = (AE_TIME);
749 #else
750         /*
751          * The interface to sem_timedwait is an absolute time, so we need to
752          * get the current time, then add in the millisecond Timeout value.
753          */
754         if (clock_gettime (CLOCK_REALTIME, &Time) == -1)
755         {
756             perror ("clock_gettime");
757             return (AE_TIME);
758         }
759
760         Time.tv_sec += (MsecTimeout / ACPI_MSEC_PER_SEC);
761         Time.tv_nsec += ((MsecTimeout % ACPI_MSEC_PER_SEC) * ACPI_NSEC_PER_MSEC);
762
763         /* Handle nanosecond overflow (field must be less than one second) */
764
765         if (Time.tv_nsec >= ACPI_NSEC_PER_SEC)
766         {
767             Time.tv_sec += (Time.tv_nsec / ACPI_NSEC_PER_SEC);
768             Time.tv_nsec = (Time.tv_nsec % ACPI_NSEC_PER_SEC);
769         }
770
771         while (((RetVal = sem_timedwait (Sem, &Time)) == -1) && (errno == EINTR))
772         {
773             continue;
774         }
775
776         if (RetVal != 0)
777         {
778             if (errno != ETIMEDOUT)
779             {
780                 perror ("sem_timedwait");
781             }
782             Status = (AE_TIME);
783         }
784 #endif
785         break;
786     }
787
788     return (Status);
789 }
790
791
792 /******************************************************************************
793  *
794  * FUNCTION:    AcpiOsSignalSemaphore
795  *
796  * PARAMETERS:  Handle              - Handle returned by AcpiOsCreateSemaphore
797  *              Units               - Number of units to send
798  *
799  * RETURN:      Status
800  *
801  * DESCRIPTION: Send units
802  *
803  *****************************************************************************/
804
805 ACPI_STATUS
806 AcpiOsSignalSemaphore (
807     ACPI_HANDLE         Handle,
808     UINT32              Units)
809 {
810     sem_t               *Sem = (sem_t *)Handle;
811
812
813     if (!Sem)
814     {
815         return (AE_BAD_PARAMETER);
816     }
817
818     if (sem_post (Sem) == -1)
819     {
820         return (AE_LIMIT);
821     }
822
823     return (AE_OK);
824 }
825
826 #endif /* ACPI_SINGLE_THREADED */
827
828
829 /******************************************************************************
830  *
831  * FUNCTION:    Spinlock interfaces
832  *
833  * DESCRIPTION: Map these interfaces to semaphore interfaces
834  *
835  *****************************************************************************/
836
837 ACPI_STATUS
838 AcpiOsCreateLock (
839     ACPI_SPINLOCK           *OutHandle)
840 {
841
842     return (AcpiOsCreateSemaphore (1, 1, OutHandle));
843 }
844
845
846 void
847 AcpiOsDeleteLock (
848     ACPI_SPINLOCK           Handle)
849 {
850     AcpiOsDeleteSemaphore (Handle);
851 }
852
853
854 ACPI_CPU_FLAGS
855 AcpiOsAcquireLock (
856     ACPI_HANDLE             Handle)
857 {
858     AcpiOsWaitSemaphore (Handle, 1, 0xFFFF);
859     return (0);
860 }
861
862
863 void
864 AcpiOsReleaseLock (
865     ACPI_SPINLOCK           Handle,
866     ACPI_CPU_FLAGS          Flags)
867 {
868     AcpiOsSignalSemaphore (Handle, 1);
869 }
870
871
872 /******************************************************************************
873  *
874  * FUNCTION:    AcpiOsInstallInterruptHandler
875  *
876  * PARAMETERS:  InterruptNumber     - Level handler should respond to.
877  *              Isr                 - Address of the ACPI interrupt handler
878  *              ExceptPtr           - Where status is returned
879  *
880  * RETURN:      Handle to the newly installed handler.
881  *
882  * DESCRIPTION: Install an interrupt handler. Used to install the ACPI
883  *              OS-independent handler.
884  *
885  *****************************************************************************/
886
887 UINT32
888 AcpiOsInstallInterruptHandler (
889     UINT32                  InterruptNumber,
890     ACPI_OSD_HANDLER        ServiceRoutine,
891     void                    *Context)
892 {
893
894     return (AE_OK);
895 }
896
897
898 /******************************************************************************
899  *
900  * FUNCTION:    AcpiOsRemoveInterruptHandler
901  *
902  * PARAMETERS:  Handle              - Returned when handler was installed
903  *
904  * RETURN:      Status
905  *
906  * DESCRIPTION: Uninstalls an interrupt handler.
907  *
908  *****************************************************************************/
909
910 ACPI_STATUS
911 AcpiOsRemoveInterruptHandler (
912     UINT32                  InterruptNumber,
913     ACPI_OSD_HANDLER        ServiceRoutine)
914 {
915
916     return (AE_OK);
917 }
918
919
920 /******************************************************************************
921  *
922  * FUNCTION:    AcpiOsStall
923  *
924  * PARAMETERS:  microseconds        - Time to sleep
925  *
926  * RETURN:      Blocks until sleep is completed.
927  *
928  * DESCRIPTION: Sleep at microsecond granularity
929  *
930  *****************************************************************************/
931
932 void
933 AcpiOsStall (
934     UINT32                  microseconds)
935 {
936
937     if (microseconds)
938     {
939         usleep (microseconds);
940     }
941 }
942
943
944 /******************************************************************************
945  *
946  * FUNCTION:    AcpiOsSleep
947  *
948  * PARAMETERS:  milliseconds        - Time to sleep
949  *
950  * RETURN:      Blocks until sleep is completed.
951  *
952  * DESCRIPTION: Sleep at millisecond granularity
953  *
954  *****************************************************************************/
955
956 void
957 AcpiOsSleep (
958     UINT64                  milliseconds)
959 {
960
961     /* Sleep for whole seconds */
962
963     sleep (milliseconds / ACPI_MSEC_PER_SEC);
964
965     /*
966      * Sleep for remaining microseconds.
967      * Arg to usleep() is in usecs and must be less than 1,000,000 (1 second).
968      */
969     usleep ((milliseconds % ACPI_MSEC_PER_SEC) * ACPI_USEC_PER_MSEC);
970 }
971
972
973 /******************************************************************************
974  *
975  * FUNCTION:    AcpiOsGetTimer
976  *
977  * PARAMETERS:  None
978  *
979  * RETURN:      Current time in 100 nanosecond units
980  *
981  * DESCRIPTION: Get the current system time
982  *
983  *****************************************************************************/
984
985 UINT64
986 AcpiOsGetTimer (
987     void)
988 {
989     struct timeval          time;
990
991
992     /* This timer has sufficient resolution for user-space application code */
993
994     gettimeofday (&time, NULL);
995
996     /* (Seconds * 10^7 = 100ns(10^-7)) + (Microseconds(10^-6) * 10^1 = 100ns) */
997
998     return (((UINT64) time.tv_sec * ACPI_100NSEC_PER_SEC) +
999             ((UINT64) time.tv_usec * ACPI_100NSEC_PER_USEC));
1000 }
1001
1002
1003 /******************************************************************************
1004  *
1005  * FUNCTION:    AcpiOsReadPciConfiguration
1006  *
1007  * PARAMETERS:  PciId               - Seg/Bus/Dev
1008  *              Register            - Device Register
1009  *              Value               - Buffer where value is placed
1010  *              Width               - Number of bits
1011  *
1012  * RETURN:      Status
1013  *
1014  * DESCRIPTION: Read data from PCI configuration space
1015  *
1016  *****************************************************************************/
1017
1018 ACPI_STATUS
1019 AcpiOsReadPciConfiguration (
1020     ACPI_PCI_ID             *PciId,
1021     UINT32                  Register,
1022     UINT64                  *Value,
1023     UINT32                  Width)
1024 {
1025
1026     *Value = 0;
1027     return (AE_OK);
1028 }
1029
1030
1031 /******************************************************************************
1032  *
1033  * FUNCTION:    AcpiOsWritePciConfiguration
1034  *
1035  * PARAMETERS:  PciId               - Seg/Bus/Dev
1036  *              Register            - Device Register
1037  *              Value               - Value to be written
1038  *              Width               - Number of bits
1039  *
1040  * RETURN:      Status.
1041  *
1042  * DESCRIPTION: Write data to PCI configuration space
1043  *
1044  *****************************************************************************/
1045
1046 ACPI_STATUS
1047 AcpiOsWritePciConfiguration (
1048     ACPI_PCI_ID             *PciId,
1049     UINT32                  Register,
1050     UINT64                  Value,
1051     UINT32                  Width)
1052 {
1053
1054     return (AE_OK);
1055 }
1056
1057
1058 /******************************************************************************
1059  *
1060  * FUNCTION:    AcpiOsReadPort
1061  *
1062  * PARAMETERS:  Address             - Address of I/O port/register to read
1063  *              Value               - Where value is placed
1064  *              Width               - Number of bits
1065  *
1066  * RETURN:      Value read from port
1067  *
1068  * DESCRIPTION: Read data from an I/O port or register
1069  *
1070  *****************************************************************************/
1071
1072 ACPI_STATUS
1073 AcpiOsReadPort (
1074     ACPI_IO_ADDRESS         Address,
1075     UINT32                  *Value,
1076     UINT32                  Width)
1077 {
1078
1079     switch (Width)
1080     {
1081     case 8:
1082
1083         *Value = 0xFF;
1084         break;
1085
1086     case 16:
1087
1088         *Value = 0xFFFF;
1089         break;
1090
1091     case 32:
1092
1093         *Value = 0xFFFFFFFF;
1094         break;
1095
1096     default:
1097
1098         return (AE_BAD_PARAMETER);
1099     }
1100
1101     return (AE_OK);
1102 }
1103
1104
1105 /******************************************************************************
1106  *
1107  * FUNCTION:    AcpiOsWritePort
1108  *
1109  * PARAMETERS:  Address             - Address of I/O port/register to write
1110  *              Value               - Value to write
1111  *              Width               - Number of bits
1112  *
1113  * RETURN:      None
1114  *
1115  * DESCRIPTION: Write data to an I/O port or register
1116  *
1117  *****************************************************************************/
1118
1119 ACPI_STATUS
1120 AcpiOsWritePort (
1121     ACPI_IO_ADDRESS         Address,
1122     UINT32                  Value,
1123     UINT32                  Width)
1124 {
1125
1126     return (AE_OK);
1127 }
1128
1129
1130 /******************************************************************************
1131  *
1132  * FUNCTION:    AcpiOsReadMemory
1133  *
1134  * PARAMETERS:  Address             - Physical Memory Address to read
1135  *              Value               - Where value is placed
1136  *              Width               - Number of bits (8,16,32, or 64)
1137  *
1138  * RETURN:      Value read from physical memory address. Always returned
1139  *              as a 64-bit integer, regardless of the read width.
1140  *
1141  * DESCRIPTION: Read data from a physical memory address
1142  *
1143  *****************************************************************************/
1144
1145 ACPI_STATUS
1146 AcpiOsReadMemory (
1147     ACPI_PHYSICAL_ADDRESS   Address,
1148     UINT64                  *Value,
1149     UINT32                  Width)
1150 {
1151
1152     switch (Width)
1153     {
1154     case 8:
1155     case 16:
1156     case 32:
1157     case 64:
1158
1159         *Value = 0;
1160         break;
1161
1162     default:
1163
1164         return (AE_BAD_PARAMETER);
1165     }
1166     return (AE_OK);
1167 }
1168
1169
1170 /******************************************************************************
1171  *
1172  * FUNCTION:    AcpiOsWriteMemory
1173  *
1174  * PARAMETERS:  Address             - Physical Memory Address to write
1175  *              Value               - Value to write
1176  *              Width               - Number of bits (8,16,32, or 64)
1177  *
1178  * RETURN:      None
1179  *
1180  * DESCRIPTION: Write data to a physical memory address
1181  *
1182  *****************************************************************************/
1183
1184 ACPI_STATUS
1185 AcpiOsWriteMemory (
1186     ACPI_PHYSICAL_ADDRESS   Address,
1187     UINT64                  Value,
1188     UINT32                  Width)
1189 {
1190
1191     return (AE_OK);
1192 }
1193
1194
1195 /******************************************************************************
1196  *
1197  * FUNCTION:    AcpiOsReadable
1198  *
1199  * PARAMETERS:  Pointer             - Area to be verified
1200  *              Length              - Size of area
1201  *
1202  * RETURN:      TRUE if readable for entire length
1203  *
1204  * DESCRIPTION: Verify that a pointer is valid for reading
1205  *
1206  *****************************************************************************/
1207
1208 BOOLEAN
1209 AcpiOsReadable (
1210     void                    *Pointer,
1211     ACPI_SIZE               Length)
1212 {
1213
1214     return (TRUE);
1215 }
1216
1217
1218 /******************************************************************************
1219  *
1220  * FUNCTION:    AcpiOsWritable
1221  *
1222  * PARAMETERS:  Pointer             - Area to be verified
1223  *              Length              - Size of area
1224  *
1225  * RETURN:      TRUE if writable for entire length
1226  *
1227  * DESCRIPTION: Verify that a pointer is valid for writing
1228  *
1229  *****************************************************************************/
1230
1231 BOOLEAN
1232 AcpiOsWritable (
1233     void                    *Pointer,
1234     ACPI_SIZE               Length)
1235 {
1236
1237     return (TRUE);
1238 }
1239
1240
1241 /******************************************************************************
1242  *
1243  * FUNCTION:    AcpiOsSignal
1244  *
1245  * PARAMETERS:  Function            - ACPI CA signal function code
1246  *              Info                - Pointer to function-dependent structure
1247  *
1248  * RETURN:      Status
1249  *
1250  * DESCRIPTION: Miscellaneous functions. Example implementation only.
1251  *
1252  *****************************************************************************/
1253
1254 ACPI_STATUS
1255 AcpiOsSignal (
1256     UINT32                  Function,
1257     void                    *Info)
1258 {
1259
1260     switch (Function)
1261     {
1262     case ACPI_SIGNAL_FATAL:
1263
1264         break;
1265
1266     case ACPI_SIGNAL_BREAKPOINT:
1267
1268         break;
1269
1270     default:
1271
1272         break;
1273     }
1274
1275     return (AE_OK);
1276 }
1277
1278 /* Optional multi-thread support */
1279
1280 #ifndef ACPI_SINGLE_THREADED
1281 /******************************************************************************
1282  *
1283  * FUNCTION:    AcpiOsGetThreadId
1284  *
1285  * PARAMETERS:  None
1286  *
1287  * RETURN:      Id of the running thread
1288  *
1289  * DESCRIPTION: Get the ID of the current (running) thread
1290  *
1291  *****************************************************************************/
1292
1293 ACPI_THREAD_ID
1294 AcpiOsGetThreadId (
1295     void)
1296 {
1297     pthread_t               thread;
1298
1299
1300     thread = pthread_self();
1301     return (ACPI_CAST_PTHREAD_T (thread));
1302 }
1303
1304
1305 /******************************************************************************
1306  *
1307  * FUNCTION:    AcpiOsExecute
1308  *
1309  * PARAMETERS:  Type                - Type of execution
1310  *              Function            - Address of the function to execute
1311  *              Context             - Passed as a parameter to the function
1312  *
1313  * RETURN:      Status.
1314  *
1315  * DESCRIPTION: Execute a new thread
1316  *
1317  *****************************************************************************/
1318
1319 ACPI_STATUS
1320 AcpiOsExecute (
1321     ACPI_EXECUTE_TYPE       Type,
1322     ACPI_OSD_EXEC_CALLBACK  Function,
1323     void                    *Context)
1324 {
1325     pthread_t               thread;
1326     int                     ret;
1327
1328
1329     ret = pthread_create (&thread, NULL, (PTHREAD_CALLBACK) Function, Context);
1330     if (ret)
1331     {
1332         AcpiOsPrintf("Create thread failed");
1333     }
1334     return (0);
1335 }
1336
1337 #endif /* ACPI_SINGLE_THREADED */
1338
1339
1340 /******************************************************************************
1341  *
1342  * FUNCTION:    AcpiOsWaitEventsComplete
1343  *
1344  * PARAMETERS:  None
1345  *
1346  * RETURN:      None
1347  *
1348  * DESCRIPTION: Wait for all asynchronous events to complete. This
1349  *              implementation does nothing.
1350  *
1351  *****************************************************************************/
1352
1353 void
1354 AcpiOsWaitEventsComplete (
1355     void)
1356 {
1357     return;
1358 }