Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0
0002 /******************************************************************************
0003  *
0004  * Module Name: osunixxf - UNIX OSL interfaces
0005  *
0006  * Copyright (C) 2000 - 2022, Intel Corp.
0007  *
0008  *****************************************************************************/
0009 
0010 /*
0011  * These interfaces are required in order to compile the ASL compiler and the
0012  * various ACPICA tools under Linux or other Unix-like system.
0013  */
0014 #include <acpi/acpi.h>
0015 #include "accommon.h"
0016 #include "amlcode.h"
0017 #include "acparser.h"
0018 #include "acdebug.h"
0019 
0020 #include <stdio.h>
0021 #include <stdlib.h>
0022 #include <stdarg.h>
0023 #include <unistd.h>
0024 #include <sys/time.h>
0025 #include <semaphore.h>
0026 #include <pthread.h>
0027 #include <errno.h>
0028 
0029 #define _COMPONENT          ACPI_OS_SERVICES
0030 ACPI_MODULE_NAME("osunixxf")
0031 
0032 /* Upcalls to acpi_exec */
0033 void
0034 ae_table_override(struct acpi_table_header *existing_table,
0035           struct acpi_table_header **new_table);
0036 
0037 typedef void *(*PTHREAD_CALLBACK) (void *);
0038 
0039 /* Buffer used by acpi_os_vprintf */
0040 
0041 #define ACPI_VPRINTF_BUFFER_SIZE    512
0042 #define _ASCII_NEWLINE              '\n'
0043 
0044 /* Terminal support for acpi_exec only */
0045 
0046 #ifdef ACPI_EXEC_APP
0047 #include <termios.h>
0048 
0049 struct termios original_term_attributes;
0050 int term_attributes_were_set = 0;
0051 
0052 acpi_status acpi_ut_read_line(char *buffer, u32 buffer_length, u32 *bytes_read);
0053 
0054 static void os_enter_line_edit_mode(void);
0055 
0056 static void os_exit_line_edit_mode(void);
0057 
0058 /******************************************************************************
0059  *
0060  * FUNCTION:    os_enter_line_edit_mode, os_exit_line_edit_mode
0061  *
0062  * PARAMETERS:  None
0063  *
0064  * RETURN:      None
0065  *
0066  * DESCRIPTION: Enter/Exit the raw character input mode for the terminal.
0067  *
0068  * Interactive line-editing support for the AML debugger. Used with the
0069  * common/acgetline module.
0070  *
0071  * readline() is not used because of non-portability. It is not available
0072  * on all systems, and if it is, often the package must be manually installed.
0073  *
0074  * Therefore, we use the POSIX tcgetattr/tcsetattr and do the minimal line
0075  * editing that we need in acpi_os_get_line.
0076  *
0077  * If the POSIX tcgetattr/tcsetattr interfaces are unavailable, these
0078  * calls will also work:
0079  *     For os_enter_line_edit_mode: system ("stty cbreak -echo")
0080  *     For os_exit_line_edit_mode: system ("stty cooked echo")
0081  *
0082  *****************************************************************************/
0083 
0084 static void os_enter_line_edit_mode(void)
0085 {
0086     struct termios local_term_attributes;
0087 
0088     term_attributes_were_set = 0;
0089 
0090     /* STDIN must be a terminal */
0091 
0092     if (!isatty(STDIN_FILENO)) {
0093         return;
0094     }
0095 
0096     /* Get and keep the original attributes */
0097 
0098     if (tcgetattr(STDIN_FILENO, &original_term_attributes)) {
0099         fprintf(stderr, "Could not get terminal attributes!\n");
0100         return;
0101     }
0102 
0103     /* Set the new attributes to enable raw character input */
0104 
0105     memcpy(&local_term_attributes, &original_term_attributes,
0106            sizeof(struct termios));
0107 
0108     local_term_attributes.c_lflag &= ~(ICANON | ECHO);
0109     local_term_attributes.c_cc[VMIN] = 1;
0110     local_term_attributes.c_cc[VTIME] = 0;
0111 
0112     if (tcsetattr(STDIN_FILENO, TCSANOW, &local_term_attributes)) {
0113         fprintf(stderr, "Could not set terminal attributes!\n");
0114         return;
0115     }
0116 
0117     term_attributes_were_set = 1;
0118 }
0119 
0120 static void os_exit_line_edit_mode(void)
0121 {
0122 
0123     if (!term_attributes_were_set) {
0124         return;
0125     }
0126 
0127     /* Set terminal attributes back to the original values */
0128 
0129     if (tcsetattr(STDIN_FILENO, TCSANOW, &original_term_attributes)) {
0130         fprintf(stderr, "Could not restore terminal attributes!\n");
0131     }
0132 }
0133 
0134 #else
0135 
0136 /* These functions are not needed for other ACPICA utilities */
0137 
0138 #define os_enter_line_edit_mode()
0139 #define os_exit_line_edit_mode()
0140 #endif
0141 
0142 /******************************************************************************
0143  *
0144  * FUNCTION:    acpi_os_initialize, acpi_os_terminate
0145  *
0146  * PARAMETERS:  None
0147  *
0148  * RETURN:      Status
0149  *
0150  * DESCRIPTION: Initialize and terminate this module.
0151  *
0152  *****************************************************************************/
0153 
0154 acpi_status acpi_os_initialize(void)
0155 {
0156     acpi_status status;
0157 
0158     acpi_gbl_output_file = stdout;
0159 
0160     os_enter_line_edit_mode();
0161 
0162     status = acpi_os_create_lock(&acpi_gbl_print_lock);
0163     if (ACPI_FAILURE(status)) {
0164         return (status);
0165     }
0166 
0167     return (AE_OK);
0168 }
0169 
0170 acpi_status acpi_os_terminate(void)
0171 {
0172 
0173     os_exit_line_edit_mode();
0174     return (AE_OK);
0175 }
0176 
0177 #ifndef ACPI_USE_NATIVE_RSDP_POINTER
0178 /******************************************************************************
0179  *
0180  * FUNCTION:    acpi_os_get_root_pointer
0181  *
0182  * PARAMETERS:  None
0183  *
0184  * RETURN:      RSDP physical address
0185  *
0186  * DESCRIPTION: Gets the ACPI root pointer (RSDP)
0187  *
0188  *****************************************************************************/
0189 
0190 acpi_physical_address acpi_os_get_root_pointer(void)
0191 {
0192 
0193     return (0);
0194 }
0195 #endif
0196 
0197 /******************************************************************************
0198  *
0199  * FUNCTION:    acpi_os_predefined_override
0200  *
0201  * PARAMETERS:  init_val            - Initial value of the predefined object
0202  *              new_val             - The new value for the object
0203  *
0204  * RETURN:      Status, pointer to value. Null pointer returned if not
0205  *              overriding.
0206  *
0207  * DESCRIPTION: Allow the OS to override predefined names
0208  *
0209  *****************************************************************************/
0210 
0211 acpi_status
0212 acpi_os_predefined_override(const struct acpi_predefined_names *init_val,
0213                 acpi_string *new_val)
0214 {
0215 
0216     if (!init_val || !new_val) {
0217         return (AE_BAD_PARAMETER);
0218     }
0219 
0220     *new_val = NULL;
0221     return (AE_OK);
0222 }
0223 
0224 /******************************************************************************
0225  *
0226  * FUNCTION:    acpi_os_table_override
0227  *
0228  * PARAMETERS:  existing_table      - Header of current table (probably
0229  *                                    firmware)
0230  *              new_table           - Where an entire new table is returned.
0231  *
0232  * RETURN:      Status, pointer to new table. Null pointer returned if no
0233  *              table is available to override
0234  *
0235  * DESCRIPTION: Return a different version of a table if one is available
0236  *
0237  *****************************************************************************/
0238 
0239 acpi_status
0240 acpi_os_table_override(struct acpi_table_header *existing_table,
0241                struct acpi_table_header **new_table)
0242 {
0243 
0244     if (!existing_table || !new_table) {
0245         return (AE_BAD_PARAMETER);
0246     }
0247 
0248     *new_table = NULL;
0249 
0250 #ifdef ACPI_EXEC_APP
0251 
0252     ae_table_override(existing_table, new_table);
0253     return (AE_OK);
0254 #else
0255 
0256     return (AE_NO_ACPI_TABLES);
0257 #endif
0258 }
0259 
0260 /******************************************************************************
0261  *
0262  * FUNCTION:    acpi_os_physical_table_override
0263  *
0264  * PARAMETERS:  existing_table      - Header of current table (probably firmware)
0265  *              new_address         - Where new table address is returned
0266  *                                    (Physical address)
0267  *              new_table_length    - Where new table length is returned
0268  *
0269  * RETURN:      Status, address/length of new table. Null pointer returned
0270  *              if no table is available to override.
0271  *
0272  * DESCRIPTION: Returns AE_SUPPORT, function not used in user space.
0273  *
0274  *****************************************************************************/
0275 
0276 acpi_status
0277 acpi_os_physical_table_override(struct acpi_table_header *existing_table,
0278                 acpi_physical_address *new_address,
0279                 u32 *new_table_length)
0280 {
0281 
0282     return (AE_SUPPORT);
0283 }
0284 
0285 /******************************************************************************
0286  *
0287  * FUNCTION:    acpi_os_enter_sleep
0288  *
0289  * PARAMETERS:  sleep_state         - Which sleep state to enter
0290  *              rega_value          - Register A value
0291  *              regb_value          - Register B value
0292  *
0293  * RETURN:      Status
0294  *
0295  * DESCRIPTION: A hook before writing sleep registers to enter the sleep
0296  *              state. Return AE_CTRL_TERMINATE to skip further sleep register
0297  *              writes.
0298  *
0299  *****************************************************************************/
0300 
0301 acpi_status acpi_os_enter_sleep(u8 sleep_state, u32 rega_value, u32 regb_value)
0302 {
0303 
0304     return (AE_OK);
0305 }
0306 
0307 /******************************************************************************
0308  *
0309  * FUNCTION:    acpi_os_redirect_output
0310  *
0311  * PARAMETERS:  destination         - An open file handle/pointer
0312  *
0313  * RETURN:      None
0314  *
0315  * DESCRIPTION: Causes redirect of acpi_os_printf and acpi_os_vprintf
0316  *
0317  *****************************************************************************/
0318 
0319 void acpi_os_redirect_output(void *destination)
0320 {
0321 
0322     acpi_gbl_output_file = destination;
0323 }
0324 
0325 /******************************************************************************
0326  *
0327  * FUNCTION:    acpi_os_printf
0328  *
0329  * PARAMETERS:  fmt, ...            - Standard printf format
0330  *
0331  * RETURN:      None
0332  *
0333  * DESCRIPTION: Formatted output. Note: very similar to acpi_os_vprintf
0334  *              (performance), changes should be tracked in both functions.
0335  *
0336  *****************************************************************************/
0337 
0338 void ACPI_INTERNAL_VAR_XFACE acpi_os_printf(const char *fmt, ...)
0339 {
0340     va_list args;
0341     u8 flags;
0342 
0343     flags = acpi_gbl_db_output_flags;
0344     if (flags & ACPI_DB_REDIRECTABLE_OUTPUT) {
0345 
0346         /* Output is directable to either a file (if open) or the console */
0347 
0348         if (acpi_gbl_debug_file) {
0349 
0350             /* Output file is open, send the output there */
0351 
0352             va_start(args, fmt);
0353             vfprintf(acpi_gbl_debug_file, fmt, args);
0354             va_end(args);
0355         } else {
0356             /* No redirection, send output to console (once only!) */
0357 
0358             flags |= ACPI_DB_CONSOLE_OUTPUT;
0359         }
0360     }
0361 
0362     if (flags & ACPI_DB_CONSOLE_OUTPUT) {
0363         va_start(args, fmt);
0364         vfprintf(acpi_gbl_output_file, fmt, args);
0365         va_end(args);
0366     }
0367 }
0368 
0369 /******************************************************************************
0370  *
0371  * FUNCTION:    acpi_os_vprintf
0372  *
0373  * PARAMETERS:  fmt                 - Standard printf format
0374  *              args                - Argument list
0375  *
0376  * RETURN:      None
0377  *
0378  * DESCRIPTION: Formatted output with argument list pointer. Note: very
0379  *              similar to acpi_os_printf, changes should be tracked in both
0380  *              functions.
0381  *
0382  *****************************************************************************/
0383 
0384 void acpi_os_vprintf(const char *fmt, va_list args)
0385 {
0386     u8 flags;
0387     char buffer[ACPI_VPRINTF_BUFFER_SIZE];
0388 
0389     /*
0390      * We build the output string in a local buffer because we may be
0391      * outputting the buffer twice. Using vfprintf is problematic because
0392      * some implementations modify the args pointer/structure during
0393      * execution. Thus, we use the local buffer for portability.
0394      *
0395      * Note: Since this module is intended for use by the various ACPICA
0396      * utilities/applications, we can safely declare the buffer on the stack.
0397      * Also, This function is used for relatively small error messages only.
0398      */
0399     vsnprintf(buffer, ACPI_VPRINTF_BUFFER_SIZE, fmt, args);
0400 
0401     flags = acpi_gbl_db_output_flags;
0402     if (flags & ACPI_DB_REDIRECTABLE_OUTPUT) {
0403 
0404         /* Output is directable to either a file (if open) or the console */
0405 
0406         if (acpi_gbl_debug_file) {
0407 
0408             /* Output file is open, send the output there */
0409 
0410             fputs(buffer, acpi_gbl_debug_file);
0411         } else {
0412             /* No redirection, send output to console (once only!) */
0413 
0414             flags |= ACPI_DB_CONSOLE_OUTPUT;
0415         }
0416     }
0417 
0418     if (flags & ACPI_DB_CONSOLE_OUTPUT) {
0419         fputs(buffer, acpi_gbl_output_file);
0420     }
0421 }
0422 
0423 #ifndef ACPI_EXEC_APP
0424 /******************************************************************************
0425  *
0426  * FUNCTION:    acpi_os_get_line
0427  *
0428  * PARAMETERS:  buffer              - Where to return the command line
0429  *              buffer_length       - Maximum length of Buffer
0430  *              bytes_read          - Where the actual byte count is returned
0431  *
0432  * RETURN:      Status and actual bytes read
0433  *
0434  * DESCRIPTION: Get the next input line from the terminal. NOTE: For the
0435  *              acpi_exec utility, we use the acgetline module instead to
0436  *              provide line-editing and history support.
0437  *
0438  *****************************************************************************/
0439 
0440 acpi_status acpi_os_get_line(char *buffer, u32 buffer_length, u32 *bytes_read)
0441 {
0442     int input_char;
0443     u32 end_of_line;
0444 
0445     /* Standard acpi_os_get_line for all utilities except acpi_exec */
0446 
0447     for (end_of_line = 0;; end_of_line++) {
0448         if (end_of_line >= buffer_length) {
0449             return (AE_BUFFER_OVERFLOW);
0450         }
0451 
0452         if ((input_char = getchar()) == EOF) {
0453             return (AE_ERROR);
0454         }
0455 
0456         if (!input_char || input_char == _ASCII_NEWLINE) {
0457             break;
0458         }
0459 
0460         buffer[end_of_line] = (char)input_char;
0461     }
0462 
0463     /* Null terminate the buffer */
0464 
0465     buffer[end_of_line] = 0;
0466 
0467     /* Return the number of bytes in the string */
0468 
0469     if (bytes_read) {
0470         *bytes_read = end_of_line;
0471     }
0472 
0473     return (AE_OK);
0474 }
0475 #endif
0476 
0477 #ifndef ACPI_USE_NATIVE_MEMORY_MAPPING
0478 /******************************************************************************
0479  *
0480  * FUNCTION:    acpi_os_map_memory
0481  *
0482  * PARAMETERS:  where               - Physical address of memory to be mapped
0483  *              length              - How much memory to map
0484  *
0485  * RETURN:      Pointer to mapped memory. Null on error.
0486  *
0487  * DESCRIPTION: Map physical memory into caller's address space
0488  *
0489  *****************************************************************************/
0490 
0491 void *acpi_os_map_memory(acpi_physical_address where, acpi_size length)
0492 {
0493 
0494     return (ACPI_TO_POINTER((acpi_size)where));
0495 }
0496 
0497 /******************************************************************************
0498  *
0499  * FUNCTION:    acpi_os_unmap_memory
0500  *
0501  * PARAMETERS:  where               - Logical address of memory to be unmapped
0502  *              length              - How much memory to unmap
0503  *
0504  * RETURN:      None.
0505  *
0506  * DESCRIPTION: Delete a previously created mapping. Where and Length must
0507  *              correspond to a previous mapping exactly.
0508  *
0509  *****************************************************************************/
0510 
0511 void acpi_os_unmap_memory(void *where, acpi_size length)
0512 {
0513 
0514     return;
0515 }
0516 #endif
0517 
0518 /******************************************************************************
0519  *
0520  * FUNCTION:    acpi_os_allocate
0521  *
0522  * PARAMETERS:  size                - Amount to allocate, in bytes
0523  *
0524  * RETURN:      Pointer to the new allocation. Null on error.
0525  *
0526  * DESCRIPTION: Allocate memory. Algorithm is dependent on the OS.
0527  *
0528  *****************************************************************************/
0529 
0530 void *acpi_os_allocate(acpi_size size)
0531 {
0532     void *mem;
0533 
0534     mem = (void *)malloc((size_t) size);
0535     return (mem);
0536 }
0537 
0538 #ifdef USE_NATIVE_ALLOCATE_ZEROED
0539 /******************************************************************************
0540  *
0541  * FUNCTION:    acpi_os_allocate_zeroed
0542  *
0543  * PARAMETERS:  size                - Amount to allocate, in bytes
0544  *
0545  * RETURN:      Pointer to the new allocation. Null on error.
0546  *
0547  * DESCRIPTION: Allocate and zero memory. Algorithm is dependent on the OS.
0548  *
0549  *****************************************************************************/
0550 
0551 void *acpi_os_allocate_zeroed(acpi_size size)
0552 {
0553     void *mem;
0554 
0555     mem = (void *)calloc(1, (size_t) size);
0556     return (mem);
0557 }
0558 #endif
0559 
0560 /******************************************************************************
0561  *
0562  * FUNCTION:    acpi_os_free
0563  *
0564  * PARAMETERS:  mem                 - Pointer to previously allocated memory
0565  *
0566  * RETURN:      None.
0567  *
0568  * DESCRIPTION: Free memory allocated via acpi_os_allocate
0569  *
0570  *****************************************************************************/
0571 
0572 void acpi_os_free(void *mem)
0573 {
0574 
0575     free(mem);
0576 }
0577 
0578 #ifdef ACPI_SINGLE_THREADED
0579 /******************************************************************************
0580  *
0581  * FUNCTION:    Semaphore stub functions
0582  *
0583  * DESCRIPTION: Stub functions used for single-thread applications that do
0584  *              not require semaphore synchronization. Full implementations
0585  *              of these functions appear after the stubs.
0586  *
0587  *****************************************************************************/
0588 
0589 acpi_status
0590 acpi_os_create_semaphore(u32 max_units,
0591              u32 initial_units, acpi_handle *out_handle)
0592 {
0593     *out_handle = (acpi_handle)1;
0594     return (AE_OK);
0595 }
0596 
0597 acpi_status acpi_os_delete_semaphore(acpi_handle handle)
0598 {
0599     return (AE_OK);
0600 }
0601 
0602 acpi_status acpi_os_wait_semaphore(acpi_handle handle, u32 units, u16 timeout)
0603 {
0604     return (AE_OK);
0605 }
0606 
0607 acpi_status acpi_os_signal_semaphore(acpi_handle handle, u32 units)
0608 {
0609     return (AE_OK);
0610 }
0611 
0612 #else
0613 /******************************************************************************
0614  *
0615  * FUNCTION:    acpi_os_create_semaphore
0616  *
0617  * PARAMETERS:  initial_units       - Units to be assigned to the new semaphore
0618  *              out_handle          - Where a handle will be returned
0619  *
0620  * RETURN:      Status
0621  *
0622  * DESCRIPTION: Create an OS semaphore
0623  *
0624  *****************************************************************************/
0625 
0626 acpi_status
0627 acpi_os_create_semaphore(u32 max_units,
0628              u32 initial_units, acpi_handle *out_handle)
0629 {
0630     sem_t *sem;
0631 
0632     if (!out_handle) {
0633         return (AE_BAD_PARAMETER);
0634     }
0635 #ifdef __APPLE__
0636     {
0637         static int semaphore_count = 0;
0638         char semaphore_name[32];
0639 
0640         snprintf(semaphore_name, sizeof(semaphore_name), "acpi_sem_%d",
0641              semaphore_count++);
0642         printf("%s\n", semaphore_name);
0643         sem =
0644             sem_open(semaphore_name, O_EXCL | O_CREAT, 0755,
0645                  initial_units);
0646         if (!sem) {
0647             return (AE_NO_MEMORY);
0648         }
0649         sem_unlink(semaphore_name); /* This just deletes the name */
0650     }
0651 
0652 #else
0653     sem = acpi_os_allocate(sizeof(sem_t));
0654     if (!sem) {
0655         return (AE_NO_MEMORY);
0656     }
0657 
0658     if (sem_init(sem, 0, initial_units) == -1) {
0659         acpi_os_free(sem);
0660         return (AE_BAD_PARAMETER);
0661     }
0662 #endif
0663 
0664     *out_handle = (acpi_handle)sem;
0665     return (AE_OK);
0666 }
0667 
0668 /******************************************************************************
0669  *
0670  * FUNCTION:    acpi_os_delete_semaphore
0671  *
0672  * PARAMETERS:  handle              - Handle returned by acpi_os_create_semaphore
0673  *
0674  * RETURN:      Status
0675  *
0676  * DESCRIPTION: Delete an OS semaphore
0677  *
0678  *****************************************************************************/
0679 
0680 acpi_status acpi_os_delete_semaphore(acpi_handle handle)
0681 {
0682     sem_t *sem = (sem_t *) handle;
0683 
0684     if (!sem) {
0685         return (AE_BAD_PARAMETER);
0686     }
0687 #ifdef __APPLE__
0688     if (sem_close(sem) == -1) {
0689         return (AE_BAD_PARAMETER);
0690     }
0691 #else
0692     if (sem_destroy(sem) == -1) {
0693         return (AE_BAD_PARAMETER);
0694     }
0695 #endif
0696 
0697     return (AE_OK);
0698 }
0699 
0700 /******************************************************************************
0701  *
0702  * FUNCTION:    acpi_os_wait_semaphore
0703  *
0704  * PARAMETERS:  handle              - Handle returned by acpi_os_create_semaphore
0705  *              units               - How many units to wait for
0706  *              msec_timeout        - How long to wait (milliseconds)
0707  *
0708  * RETURN:      Status
0709  *
0710  * DESCRIPTION: Wait for units
0711  *
0712  *****************************************************************************/
0713 
0714 acpi_status
0715 acpi_os_wait_semaphore(acpi_handle handle, u32 units, u16 msec_timeout)
0716 {
0717     acpi_status status = AE_OK;
0718     sem_t *sem = (sem_t *) handle;
0719     int ret_val;
0720 #ifndef ACPI_USE_ALTERNATE_TIMEOUT
0721     struct timespec time;
0722 #endif
0723 
0724     if (!sem) {
0725         return (AE_BAD_PARAMETER);
0726     }
0727 
0728     switch (msec_timeout) {
0729         /*
0730          * No Wait:
0731          * --------
0732          * A zero timeout value indicates that we shouldn't wait - just
0733          * acquire the semaphore if available otherwise return AE_TIME
0734          * (a.k.a. 'would block').
0735          */
0736     case 0:
0737 
0738         if (sem_trywait(sem) == -1) {
0739             status = (AE_TIME);
0740         }
0741         break;
0742 
0743         /* Wait Indefinitely */
0744 
0745     case ACPI_WAIT_FOREVER:
0746 
0747         while (((ret_val = sem_wait(sem)) == -1) && (errno == EINTR)) {
0748             continue;   /* Restart if interrupted */
0749         }
0750         if (ret_val != 0) {
0751             status = (AE_TIME);
0752         }
0753         break;
0754 
0755         /* Wait with msec_timeout */
0756 
0757     default:
0758 
0759 #ifdef ACPI_USE_ALTERNATE_TIMEOUT
0760         /*
0761          * Alternate timeout mechanism for environments where
0762          * sem_timedwait is not available or does not work properly.
0763          */
0764         while (msec_timeout) {
0765             if (sem_trywait(sem) == 0) {
0766 
0767                 /* Got the semaphore */
0768                 return (AE_OK);
0769             }
0770 
0771             if (msec_timeout >= 10) {
0772                 msec_timeout -= 10;
0773                 usleep(10 * ACPI_USEC_PER_MSEC);    /* ten milliseconds */
0774             } else {
0775                 msec_timeout--;
0776                 usleep(ACPI_USEC_PER_MSEC); /* one millisecond */
0777             }
0778         }
0779         status = (AE_TIME);
0780 #else
0781         /*
0782          * The interface to sem_timedwait is an absolute time, so we need to
0783          * get the current time, then add in the millisecond Timeout value.
0784          */
0785         if (clock_gettime(CLOCK_REALTIME, &time) == -1) {
0786             perror("clock_gettime");
0787             return (AE_TIME);
0788         }
0789 
0790         time.tv_sec += (msec_timeout / ACPI_MSEC_PER_SEC);
0791         time.tv_nsec +=
0792             ((msec_timeout % ACPI_MSEC_PER_SEC) * ACPI_NSEC_PER_MSEC);
0793 
0794         /* Handle nanosecond overflow (field must be less than one second) */
0795 
0796         if (time.tv_nsec >= ACPI_NSEC_PER_SEC) {
0797             time.tv_sec += (time.tv_nsec / ACPI_NSEC_PER_SEC);
0798             time.tv_nsec = (time.tv_nsec % ACPI_NSEC_PER_SEC);
0799         }
0800 
0801         while (((ret_val = sem_timedwait(sem, &time)) == -1)
0802                && (errno == EINTR)) {
0803             continue;   /* Restart if interrupted */
0804 
0805         }
0806 
0807         if (ret_val != 0) {
0808             if (errno != ETIMEDOUT) {
0809                 perror("sem_timedwait");
0810             }
0811             status = (AE_TIME);
0812         }
0813 #endif
0814         break;
0815     }
0816 
0817     return (status);
0818 }
0819 
0820 /******************************************************************************
0821  *
0822  * FUNCTION:    acpi_os_signal_semaphore
0823  *
0824  * PARAMETERS:  handle              - Handle returned by acpi_os_create_semaphore
0825  *              units               - Number of units to send
0826  *
0827  * RETURN:      Status
0828  *
0829  * DESCRIPTION: Send units
0830  *
0831  *****************************************************************************/
0832 
0833 acpi_status acpi_os_signal_semaphore(acpi_handle handle, u32 units)
0834 {
0835     sem_t *sem = (sem_t *) handle;
0836 
0837     if (!sem) {
0838         return (AE_BAD_PARAMETER);
0839     }
0840 
0841     if (sem_post(sem) == -1) {
0842         return (AE_LIMIT);
0843     }
0844 
0845     return (AE_OK);
0846 }
0847 
0848 #endif              /* ACPI_SINGLE_THREADED */
0849 
0850 /******************************************************************************
0851  *
0852  * FUNCTION:    Spinlock interfaces
0853  *
0854  * DESCRIPTION: Map these interfaces to semaphore interfaces
0855  *
0856  *****************************************************************************/
0857 
0858 acpi_status acpi_os_create_lock(acpi_spinlock * out_handle)
0859 {
0860 
0861     return (acpi_os_create_semaphore(1, 1, out_handle));
0862 }
0863 
0864 void acpi_os_delete_lock(acpi_spinlock handle)
0865 {
0866     acpi_os_delete_semaphore(handle);
0867 }
0868 
0869 acpi_cpu_flags acpi_os_acquire_lock(acpi_handle handle)
0870 {
0871     acpi_os_wait_semaphore(handle, 1, 0xFFFF);
0872     return (0);
0873 }
0874 
0875 void acpi_os_release_lock(acpi_spinlock handle, acpi_cpu_flags flags)
0876 {
0877     acpi_os_signal_semaphore(handle, 1);
0878 }
0879 
0880 /******************************************************************************
0881  *
0882  * FUNCTION:    acpi_os_install_interrupt_handler
0883  *
0884  * PARAMETERS:  interrupt_number    - Level handler should respond to.
0885  *              isr                 - Address of the ACPI interrupt handler
0886  *              except_ptr          - Where status is returned
0887  *
0888  * RETURN:      Handle to the newly installed handler.
0889  *
0890  * DESCRIPTION: Install an interrupt handler. Used to install the ACPI
0891  *              OS-independent handler.
0892  *
0893  *****************************************************************************/
0894 
0895 u32
0896 acpi_os_install_interrupt_handler(u32 interrupt_number,
0897                   acpi_osd_handler service_routine,
0898                   void *context)
0899 {
0900 
0901     return (AE_OK);
0902 }
0903 
0904 /******************************************************************************
0905  *
0906  * FUNCTION:    acpi_os_remove_interrupt_handler
0907  *
0908  * PARAMETERS:  handle              - Returned when handler was installed
0909  *
0910  * RETURN:      Status
0911  *
0912  * DESCRIPTION: Uninstalls an interrupt handler.
0913  *
0914  *****************************************************************************/
0915 
0916 acpi_status
0917 acpi_os_remove_interrupt_handler(u32 interrupt_number,
0918                  acpi_osd_handler service_routine)
0919 {
0920 
0921     return (AE_OK);
0922 }
0923 
0924 /******************************************************************************
0925  *
0926  * FUNCTION:    acpi_os_stall
0927  *
0928  * PARAMETERS:  microseconds        - Time to sleep
0929  *
0930  * RETURN:      Blocks until sleep is completed.
0931  *
0932  * DESCRIPTION: Sleep at microsecond granularity
0933  *
0934  *****************************************************************************/
0935 
0936 void acpi_os_stall(u32 microseconds)
0937 {
0938 
0939     if (microseconds) {
0940         usleep(microseconds);
0941     }
0942 }
0943 
0944 /******************************************************************************
0945  *
0946  * FUNCTION:    acpi_os_sleep
0947  *
0948  * PARAMETERS:  milliseconds        - Time to sleep
0949  *
0950  * RETURN:      Blocks until sleep is completed.
0951  *
0952  * DESCRIPTION: Sleep at millisecond granularity
0953  *
0954  *****************************************************************************/
0955 
0956 void acpi_os_sleep(u64 milliseconds)
0957 {
0958 
0959     /* Sleep for whole seconds */
0960 
0961     sleep(milliseconds / ACPI_MSEC_PER_SEC);
0962 
0963     /*
0964      * Sleep for remaining microseconds.
0965      * Arg to usleep() is in usecs and must be less than 1,000,000 (1 second).
0966      */
0967     usleep((milliseconds % ACPI_MSEC_PER_SEC) * ACPI_USEC_PER_MSEC);
0968 }
0969 
0970 /******************************************************************************
0971  *
0972  * FUNCTION:    acpi_os_get_timer
0973  *
0974  * PARAMETERS:  None
0975  *
0976  * RETURN:      Current time in 100 nanosecond units
0977  *
0978  * DESCRIPTION: Get the current system time
0979  *
0980  *****************************************************************************/
0981 
0982 u64 acpi_os_get_timer(void)
0983 {
0984     struct timeval time;
0985 
0986     /* This timer has sufficient resolution for user-space application code */
0987 
0988     gettimeofday(&time, NULL);
0989 
0990     /* (Seconds * 10^7 = 100ns(10^-7)) + (Microseconds(10^-6) * 10^1 = 100ns) */
0991 
0992     return (((u64)time.tv_sec * ACPI_100NSEC_PER_SEC) +
0993         ((u64)time.tv_usec * ACPI_100NSEC_PER_USEC));
0994 }
0995 
0996 /******************************************************************************
0997  *
0998  * FUNCTION:    acpi_os_read_pci_configuration
0999  *
1000  * PARAMETERS:  pci_id              - Seg/Bus/Dev
1001  *              pci_register        - Device Register
1002  *              value               - Buffer where value is placed
1003  *              width               - Number of bits
1004  *
1005  * RETURN:      Status
1006  *
1007  * DESCRIPTION: Read data from PCI configuration space
1008  *
1009  *****************************************************************************/
1010 
1011 acpi_status
1012 acpi_os_read_pci_configuration(struct acpi_pci_id *pci_id,
1013                    u32 pci_register, u64 *value, u32 width)
1014 {
1015 
1016     *value = 0;
1017     return (AE_OK);
1018 }
1019 
1020 /******************************************************************************
1021  *
1022  * FUNCTION:    acpi_os_write_pci_configuration
1023  *
1024  * PARAMETERS:  pci_id              - Seg/Bus/Dev
1025  *              pci_register        - Device Register
1026  *              value               - Value to be written
1027  *              width               - Number of bits
1028  *
1029  * RETURN:      Status.
1030  *
1031  * DESCRIPTION: Write data to PCI configuration space
1032  *
1033  *****************************************************************************/
1034 
1035 acpi_status
1036 acpi_os_write_pci_configuration(struct acpi_pci_id *pci_id,
1037                 u32 pci_register, u64 value, u32 width)
1038 {
1039 
1040     return (AE_OK);
1041 }
1042 
1043 /******************************************************************************
1044  *
1045  * FUNCTION:    acpi_os_read_port
1046  *
1047  * PARAMETERS:  address             - Address of I/O port/register to read
1048  *              value               - Where value is placed
1049  *              width               - Number of bits
1050  *
1051  * RETURN:      Value read from port
1052  *
1053  * DESCRIPTION: Read data from an I/O port or register
1054  *
1055  *****************************************************************************/
1056 
1057 acpi_status acpi_os_read_port(acpi_io_address address, u32 *value, u32 width)
1058 {
1059 
1060     switch (width) {
1061     case 8:
1062 
1063         *value = 0xFF;
1064         break;
1065 
1066     case 16:
1067 
1068         *value = 0xFFFF;
1069         break;
1070 
1071     case 32:
1072 
1073         *value = 0xFFFFFFFF;
1074         break;
1075 
1076     default:
1077 
1078         return (AE_BAD_PARAMETER);
1079     }
1080 
1081     return (AE_OK);
1082 }
1083 
1084 /******************************************************************************
1085  *
1086  * FUNCTION:    acpi_os_write_port
1087  *
1088  * PARAMETERS:  address             - Address of I/O port/register to write
1089  *              value               - Value to write
1090  *              width               - Number of bits
1091  *
1092  * RETURN:      None
1093  *
1094  * DESCRIPTION: Write data to an I/O port or register
1095  *
1096  *****************************************************************************/
1097 
1098 acpi_status acpi_os_write_port(acpi_io_address address, u32 value, u32 width)
1099 {
1100 
1101     return (AE_OK);
1102 }
1103 
1104 /******************************************************************************
1105  *
1106  * FUNCTION:    acpi_os_read_memory
1107  *
1108  * PARAMETERS:  address             - Physical Memory Address to read
1109  *              value               - Where value is placed
1110  *              width               - Number of bits (8,16,32, or 64)
1111  *
1112  * RETURN:      Value read from physical memory address. Always returned
1113  *              as a 64-bit integer, regardless of the read width.
1114  *
1115  * DESCRIPTION: Read data from a physical memory address
1116  *
1117  *****************************************************************************/
1118 
1119 acpi_status
1120 acpi_os_read_memory(acpi_physical_address address, u64 *value, u32 width)
1121 {
1122 
1123     switch (width) {
1124     case 8:
1125     case 16:
1126     case 32:
1127     case 64:
1128 
1129         *value = 0;
1130         break;
1131 
1132     default:
1133 
1134         return (AE_BAD_PARAMETER);
1135     }
1136     return (AE_OK);
1137 }
1138 
1139 /******************************************************************************
1140  *
1141  * FUNCTION:    acpi_os_write_memory
1142  *
1143  * PARAMETERS:  address             - Physical Memory Address to write
1144  *              value               - Value to write
1145  *              width               - Number of bits (8,16,32, or 64)
1146  *
1147  * RETURN:      None
1148  *
1149  * DESCRIPTION: Write data to a physical memory address
1150  *
1151  *****************************************************************************/
1152 
1153 acpi_status
1154 acpi_os_write_memory(acpi_physical_address address, u64 value, u32 width)
1155 {
1156 
1157     return (AE_OK);
1158 }
1159 
1160 /******************************************************************************
1161  *
1162  * FUNCTION:    acpi_os_readable
1163  *
1164  * PARAMETERS:  pointer             - Area to be verified
1165  *              length              - Size of area
1166  *
1167  * RETURN:      TRUE if readable for entire length
1168  *
1169  * DESCRIPTION: Verify that a pointer is valid for reading
1170  *
1171  *****************************************************************************/
1172 
1173 u8 acpi_os_readable(void *pointer, acpi_size length)
1174 {
1175 
1176     return (TRUE);
1177 }
1178 
1179 /******************************************************************************
1180  *
1181  * FUNCTION:    acpi_os_writable
1182  *
1183  * PARAMETERS:  pointer             - Area to be verified
1184  *              length              - Size of area
1185  *
1186  * RETURN:      TRUE if writable for entire length
1187  *
1188  * DESCRIPTION: Verify that a pointer is valid for writing
1189  *
1190  *****************************************************************************/
1191 
1192 u8 acpi_os_writable(void *pointer, acpi_size length)
1193 {
1194 
1195     return (TRUE);
1196 }
1197 
1198 /******************************************************************************
1199  *
1200  * FUNCTION:    acpi_os_signal
1201  *
1202  * PARAMETERS:  function            - ACPI A signal function code
1203  *              info                - Pointer to function-dependent structure
1204  *
1205  * RETURN:      Status
1206  *
1207  * DESCRIPTION: Miscellaneous functions. Example implementation only.
1208  *
1209  *****************************************************************************/
1210 
1211 acpi_status acpi_os_signal(u32 function, void *info)
1212 {
1213 
1214     switch (function) {
1215     case ACPI_SIGNAL_FATAL:
1216 
1217         break;
1218 
1219     case ACPI_SIGNAL_BREAKPOINT:
1220 
1221         break;
1222 
1223     default:
1224 
1225         break;
1226     }
1227 
1228     return (AE_OK);
1229 }
1230 
1231 /* Optional multi-thread support */
1232 
1233 #ifndef ACPI_SINGLE_THREADED
1234 /******************************************************************************
1235  *
1236  * FUNCTION:    acpi_os_get_thread_id
1237  *
1238  * PARAMETERS:  None
1239  *
1240  * RETURN:      Id of the running thread
1241  *
1242  * DESCRIPTION: Get the ID of the current (running) thread
1243  *
1244  *****************************************************************************/
1245 
1246 acpi_thread_id acpi_os_get_thread_id(void)
1247 {
1248     pthread_t thread;
1249 
1250     thread = pthread_self();
1251     return (ACPI_CAST_PTHREAD_T(thread));
1252 }
1253 
1254 /******************************************************************************
1255  *
1256  * FUNCTION:    acpi_os_execute
1257  *
1258  * PARAMETERS:  type                - Type of execution
1259  *              function            - Address of the function to execute
1260  *              context             - Passed as a parameter to the function
1261  *
1262  * RETURN:      Status.
1263  *
1264  * DESCRIPTION: Execute a new thread
1265  *
1266  *****************************************************************************/
1267 
1268 acpi_status
1269 acpi_os_execute(acpi_execute_type type,
1270         acpi_osd_exec_callback function, void *context)
1271 {
1272     pthread_t thread;
1273     int ret;
1274 
1275     ret =
1276         pthread_create(&thread, NULL, (PTHREAD_CALLBACK) function, context);
1277     if (ret) {
1278         acpi_os_printf("Create thread failed");
1279     }
1280     return (0);
1281 }
1282 
1283 #else               /* ACPI_SINGLE_THREADED */
1284 acpi_thread_id acpi_os_get_thread_id(void)
1285 {
1286     return (1);
1287 }
1288 
1289 acpi_status
1290 acpi_os_execute(acpi_execute_type type,
1291         acpi_osd_exec_callback function, void *context)
1292 {
1293 
1294     function(context);
1295 
1296     return (AE_OK);
1297 }
1298 
1299 #endif              /* ACPI_SINGLE_THREADED */
1300 
1301 /******************************************************************************
1302  *
1303  * FUNCTION:    acpi_os_wait_events_complete
1304  *
1305  * PARAMETERS:  None
1306  *
1307  * RETURN:      None
1308  *
1309  * DESCRIPTION: Wait for all asynchronous events to complete. This
1310  *              implementation does nothing.
1311  *
1312  *****************************************************************************/
1313 
1314 void acpi_os_wait_events_complete(void)
1315 {
1316     return;
1317 }