#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <signal.h>
#include <getopt.h>
#include <termios.h>
#include <cfg/os.h>
#include <sys/types.h>
#include <sys/event.h>
#include <sys/device.h>
#include <sys/osdebug.h>
#include <sys/atom.h>
#include <dev/irqreg.h>
#include <dev/unix_devs.h>
Defines | |
#define | NUT_THREAD_MAINSTACK 1024 |
#define | NUT_THREAD_IDLESTACK 1024 |
#define | MAX_IRQ_SLOTS 3 |
#define | PSEUDO_RAM_SIZE 999999 |
Nut/OS Initialization. | |
Functions | |
void | NutAppMain (void *arg) |
int | NutRegisterIrqHandler (uint8_t irq, void(*handler)(void *), void *arg) |
Register an interrupt handler. | |
void | NutUnixIrqEventPostAsync (uint8_t irq, HANDLE *queue) |
Register NutEventPostAsync for next NutThreadYield. | |
void | NutUnixThreadYieldHook (void) |
Handle interrupt triggered NutEventPostAsync Check list of events to post and call NutEventPostAsync on them. | |
void | NutUnixRaiseInterrupt (int) |
void * | NutInterruptEmulation (void *unused_arg) |
Send emulated interrupt signal to Nut threads. | |
void | NutIdle (void *arg) |
Emulated idle thread. | |
void | NutThreadInit (void) |
Initialize thread handling in the Linux emulation. | |
NUTFILE * | NUT_freopen (const char *name, const char *mode, NUTFILE *stream) |
int | main (int argc, char *argv[]) |
Variables | |
int | interrupts_pending [MAX_IRQ_SLOTS] |
sigset_t | irq_signal |
uint16_t | int_disabled |
int | irq_current = 0 |
int | irq_slot = 0 |
int | irq_sent = 0 |
pthread_mutex_t | pending_mutex |
pthread_cond_t | pending_cv |
pthread_mutex_t | irq_mutex |
pthread_cond_t | irq_cv |
IRQ_HANDLER | irq_handlers [IRQ_MAX] |
HANDLE * | irq_eventqueues [IRQ_MAX] |
uint32_t | nut_ticks |
Emulate a Nut hardware interrupt on Unix. | |
uint8_t | PSEUDO_RAM [PSEUDO_RAM_SIZE] |
NUTFILE * | __iob [] |
#define NUT_THREAD_MAINSTACK 1024 |
Referenced by NutIdle().
#define NUT_THREAD_IDLESTACK 1024 |
Referenced by main().
#define MAX_IRQ_SLOTS 3 |
Referenced by NutUnixRaiseInterrupt().
void NutAppMain | ( | void * | arg | ) |
int NutRegisterIrqHandler | ( | uint8_t | irq, |
void(*)(void *) | handler, | ||
void * | arg | ||
) |
Register an interrupt handler.
This function is typically called by device drivers.
irq | Interrupt number to be associated with this handler. |
handler | This routine will be called by Nut/OS, when the specified interrupt occurs. |
arg | Argument to be passed to the interrupt handler. |
References IRQ_HANDLER::ir_arg, IRQ_HANDLER::ir_handler, IRQ_MAX, NutEnterCritical, and NutExitCritical.
Register NutEventPostAsync for next NutThreadYield.
Store responsible IRQ and queue to signal in list
irq | responsible IRQ |
queue | to signal |
this is added to allow an non-nut thread to post events without introducing a race-condition
References IRQ_MAX.
void NutUnixThreadYieldHook | ( | void | ) |
Handle interrupt triggered NutEventPostAsync Check list of events to post and call NutEventPostAsync on them.
this is added to allow an non-nut thread to post events without introducing a race-condition
References IRQ_MAX, and NutEventPostFromIrq.
Referenced by NutThreadYield().
void NutUnixRaiseInterrupt | ( | int | irq | ) |
References irq_slot, MAX_IRQ_SLOTS, and printf.
Referenced by NutTimerEmulation().
void* NutInterruptEmulation | ( | void * | unused_arg | ) |
Send emulated interrupt signal to Nut threads.
Hardware devices, such as timer, usart, etc., raise interrupts to get serviced by NutOS. This function does the same for devices on Unix emulation.
irq | IRQ raised |
The Nut thread is interrupted using the SIGUSR1 signal. The corresponding signal handler dispatches to the respective interrupt handler. All IRQs are multiplexed through the same signal handler.
Signalling the interrupt is done in a separate thread so that the "calling/interrupting" thread can go back to emulate the hardware. Otherwise, in case of disabled interrupts, it would be hanging and waiting for interrupts to be re-enabled.
This thread here does nothing but signal interrupts and can safely hang it they are disabled (by NutEnterCritical, for example).
int interrupts_pending[MAX_IRQ_SLOTS] |
sigset_t irq_signal |
Referenced by NutThreadCreate(), and NutTimerEmulation().
int irq_current = 0 |
int irq_slot = 0 |
Referenced by NutInterruptEmulation(), and NutUnixRaiseInterrupt().
int irq_sent = 0 |
pthread_mutex_t pending_mutex |
pthread_cond_t pending_cv |
pthread_mutex_t irq_mutex |
pthread_cond_t irq_cv |
IRQ_HANDLER irq_handlers[IRQ_MAX] |
HANDLE* irq_eventqueues[IRQ_MAX] |