osunixxf.c revision 254745
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
68extern FILE                    *AcpiGbl_DebugFile;
69FILE                           *AcpiGbl_OutputFile;
70
71
72/* Upcalls to AcpiExec */
73
74ACPI_PHYSICAL_ADDRESS
75AeLocalGetRootPointer (
76    void);
77
78void
79AeTableOverride (
80    ACPI_TABLE_HEADER       *ExistingTable,
81    ACPI_TABLE_HEADER       **NewTable);
82
83typedef 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
102ACPI_STATUS
103AcpiOsInitialize (
104    void)
105{
106
107    AcpiGbl_OutputFile = stdout;
108    return (AE_OK);
109}
110
111
112ACPI_STATUS
113AcpiOsTerminate (
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
133ACPI_PHYSICAL_ADDRESS
134AcpiOsGetRootPointer (
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
156ACPI_STATUS
157AcpiOsPredefinedOverride (
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
187ACPI_STATUS
188AcpiOsTableOverride (
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
227ACPI_STATUS
228AcpiOsPhysicalTableOverride (
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
250void
251AcpiOsRedirectOutput (
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
272void ACPI_INTERNAL_VAR_XFACE
273AcpiOsPrintf (
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
326void
327AcpiOsVprintf (
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
387ACPI_STATUS
388AcpiOsGetLine (
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
444void *
445AcpiOsMapMemory (
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
468void
469AcpiOsUnmapMemory (
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
490void *
491AcpiOsAllocate (
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
514void
515AcpiOsFree (
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
534ACPI_STATUS
535AcpiOsCreateSemaphore (
536    UINT32              MaxUnits,
537    UINT32              InitialUnits,
538    ACPI_HANDLE         *OutHandle)
539{
540    *OutHandle = (ACPI_HANDLE) 1;
541    return (AE_OK);
542}
543
544ACPI_STATUS
545AcpiOsDeleteSemaphore (
546    ACPI_HANDLE         Handle)
547{
548    return (AE_OK);
549}
550
551ACPI_STATUS
552AcpiOsWaitSemaphore (
553    ACPI_HANDLE         Handle,
554    UINT32              Units,
555    UINT16              Timeout)
556{
557    return (AE_OK);
558}
559
560ACPI_STATUS
561AcpiOsSignalSemaphore (
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
582ACPI_STATUS
583AcpiOsCreateSemaphore (
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
639ACPI_STATUS
640AcpiOsDeleteSemaphore (
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
674ACPI_STATUS
675AcpiOsWaitSemaphore (
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
805ACPI_STATUS
806AcpiOsSignalSemaphore (
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
837ACPI_STATUS
838AcpiOsCreateLock (
839    ACPI_SPINLOCK           *OutHandle)
840{
841
842    return (AcpiOsCreateSemaphore (1, 1, OutHandle));
843}
844
845
846void
847AcpiOsDeleteLock (
848    ACPI_SPINLOCK           Handle)
849{
850    AcpiOsDeleteSemaphore (Handle);
851}
852
853
854ACPI_CPU_FLAGS
855AcpiOsAcquireLock (
856    ACPI_HANDLE             Handle)
857{
858    AcpiOsWaitSemaphore (Handle, 1, 0xFFFF);
859    return (0);
860}
861
862
863void
864AcpiOsReleaseLock (
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
887UINT32
888AcpiOsInstallInterruptHandler (
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
910ACPI_STATUS
911AcpiOsRemoveInterruptHandler (
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
932void
933AcpiOsStall (
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
956void
957AcpiOsSleep (
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
985UINT64
986AcpiOsGetTimer (
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
1018ACPI_STATUS
1019AcpiOsReadPciConfiguration (
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
1046ACPI_STATUS
1047AcpiOsWritePciConfiguration (
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
1072ACPI_STATUS
1073AcpiOsReadPort (
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
1119ACPI_STATUS
1120AcpiOsWritePort (
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
1145ACPI_STATUS
1146AcpiOsReadMemory (
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
1184ACPI_STATUS
1185AcpiOsWriteMemory (
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
1208BOOLEAN
1209AcpiOsReadable (
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
1231BOOLEAN
1232AcpiOsWritable (
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
1254ACPI_STATUS
1255AcpiOsSignal (
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
1293ACPI_THREAD_ID
1294AcpiOsGetThreadId (
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
1319ACPI_STATUS
1320AcpiOsExecute (
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
1353void
1354AcpiOsWaitEventsComplete (
1355    void)
1356{
1357    return;
1358}
1359