MonkOS  v0.1
A simple 64-bit operating system (x86_64)
timer.c
Go to the documentation of this file.
1 //============================================================================
2 /// @file timer.c
3 /// @brief Programmable interval timer (8253/8254) controller.
4 //
5 // Copyright 2016 Brett Vickers.
6 // Use of this source code is governed by a BSD-style license that can
7 // be found in the MonkOS LICENSE file.
8 //============================================================================
9 
10 #include <core.h>
11 #include <kernel/x86/cpu.h>
12 #include <kernel/device/timer.h>
14 
15 // 8253 timer ports
16 #define TIMER_PORT_DATA_CH0 0x40 ///< Channel 0 data port.
17 #define TIMER_PORT_DATA_CH1 0x41 ///< Channel 1 data port.
18 #define TIMER_PORT_DATA_CH2 0x42 ///< Channel 2 data port.
19 #define TIMER_PORT_CMD 0x43 ///< Timer command port.
20 
21 // Frequency bounds
22 #define MIN_FREQUENCY 19
23 #define MAX_FREQUENCY 1193181
24 
25 static void
26 isr_timer(const interrupt_context_t *context)
27 {
28  (void)context;
29 
30  // Do nothing for now.
31 
32  // Send the end-of-interrupt signal.
34 }
35 
36 void
37 timer_init(uint32_t frequency)
38 {
39  // Clamp frequency to allowable range.
40  if (frequency < MIN_FREQUENCY) {
41  frequency = MIN_FREQUENCY;
42  }
43  else if (frequency > MAX_FREQUENCY) {
44  frequency = MAX_FREQUENCY;
45  }
46 
47  // Compute the clock count value.
48  uint16_t count = (uint16_t)(MAX_FREQUENCY / frequency);
49 
50  // Channel=0, AccessMode=lo/hi, OperatingMode=rate-generator
51  io_outb(TIMER_PORT_CMD, 0x34);
52 
53  // Output the lo/hi count value
54  io_outb(TIMER_PORT_DATA_CH0, (uint8_t)count);
55  io_outb(TIMER_PORT_DATA_CH0, (uint8_t)(count >> 8));
56 
57  // Assign the interrupt service routine.
59 
60  // Enable the timer interrupt (IRQ0).
62 }
63 
64 void
66 {
67  // Enable the timer interrupt (IRQ0).
68  irq_enable(0);
69 }
70 
71 void
73 {
74  // Disable the timer interrupt (IRQ0).
75  irq_disable(0);
76 }
#define PIC_PORT_CMD_MASTER
Command port for master PIC.
Definition: interrupt.h:28
__forceinline void io_outb(uint16_t port, uint8_t value)
Definition: cpu_inl.h:59
#define PIC_CMD_EOI
End of interrupt.
Definition: interrupt.h:34
void timer_enable()
Enable timer interrupts.
Definition: timer.c:65
void isr_set(int interrupt, isr_handler handler)
Set an interrupt service routine for the given interrupt number.
Core include file.
void irq_disable(uint8_t irq)
Tell the PIC to disable a hardware interrupt.
#define TRAP_IRQ_TIMER
Definition: interrupt.h:24
Programmable interval timer (8253/8254) controller.
#define TIMER_PORT_DATA_CH0
Channel 0 data port.
Definition: timer.c:16
static void isr_timer(const interrupt_context_t *context)
Definition: timer.c:26
void timer_init(uint32_t frequency)
Initialize the timer controller so that it interrupts the kernel at the requested frequency...
Definition: timer.c:37
Interrupt handling operations.
x86 CPU-specific function implementations.
void irq_enable(uint8_t irq)
Tell the PIC to enable a hardware interrupt.
#define IRQ_TIMER
Definition: interrupt.h:20
The log context describes the state of the log buffers.
Definition: log.c:46
void timer_disable()
Disable timer interrupts.
Definition: timer.c:72
#define MAX_FREQUENCY
Definition: timer.c:23
#define TIMER_PORT_CMD
Timer command port.
Definition: timer.c:19
#define MIN_FREQUENCY
Definition: timer.c:22