Revision 15
Added mouse.c, mouse.h and i8024.h; Haven't made mouse_enable_date_reporting() function (corrected)
lab4/i8042.h | ||
---|---|---|
1 |
#ifndef _LCOM_I8042_H_ |
|
2 |
#define _LCOM_I8042_H_ |
|
3 |
|
|
4 |
#include <lcom/lcf.h> |
|
5 |
|
|
6 |
/** @defgroup i8042 i8042 |
|
7 |
* @{ |
|
8 |
* |
|
9 |
* Constants for programming the i8042 Keyboard. |
|
10 |
*/ |
|
11 |
|
|
12 |
//#define KEYBOARD_IRQ 0x09 /* Keyboard IRQ address */ |
|
13 |
|
|
14 |
//#define BIT(n) (0x01<<(n)) |
|
15 |
|
|
16 |
#define DELAY_US 20000 |
|
17 |
|
|
18 |
#define STAT_REG_PAR BIT(7) /* Parity Error */ |
|
19 |
#define STAT_REG_TIMEOUT BIT(6) /* Timeout Error */ |
|
20 |
#define STAT_REG_AUX BIT(5) /* Mouse Data */ |
|
21 |
#define STAT_REG_INH BIT(4) /* Inhibit Flag */ |
|
22 |
#define STAT_REG_A2 BIT(3) /* A2 Input Line */ |
|
23 |
#define STAT_REG_SYS BIT(2) /* System Flag */ |
|
24 |
#define STAT_REG_IBF BIT(1) /* Input Buffer Full */ |
|
25 |
#define STAT_REG_OBF BIT(0) /* Output Buffer Full */ |
|
26 |
|
|
27 |
#define READ_COMMAND 0x20 /* Returns Command Byte */ |
|
28 |
|
|
29 |
#define OUTPUT_BUF 0x60 /* Output Buffer */ |
|
30 |
#define INPUT_BUF 0x60 /* Input Buffer */ |
|
31 |
#define STATUS_REG 0x64 /* Status Register */ |
|
32 |
#define KBC_CMD_REG 0x64 /* Command Register */ |
|
33 |
#define INT_ENABLE BIT(0) /*enable interrupt on OBF, from keyboard*/ |
|
34 |
#define KBC_CMD_ARG 0x60 /* Command Arguments Adress */ |
|
35 |
|
|
36 |
#define ESC_BREAK 0x81 |
|
37 |
#define TWO_BYTE_SCANCODE 0xE0 /* Two-byte long scancodes use 0xE0 as their first byte */ |
|
38 |
#define MAKE_CODE BIT(7) |
|
39 |
|
|
40 |
#endif /* _LCOM_I8042_H */ |
lab4/mouse.c | ||
---|---|---|
1 |
#include "mouse.c" |
|
2 |
|
|
3 |
uint8_t byte; |
|
4 |
|
|
5 |
int (util_sys_inb)(int port, uint8_t *value) { //transform 8 bit into 32 bit |
|
6 |
|
|
7 |
uint32_t new_val; //initializing 32 bit variable |
|
8 |
|
|
9 |
if(sys_inb(port,&new_val)!=0){ //verifies if there is an error |
|
10 |
printf("Error in util_sys_inb\n"); |
|
11 |
return 1; |
|
12 |
} |
|
13 |
*value=new_val & 0xFF; //dereferencing "value" |
|
14 |
#ifdef LAB3 |
|
15 |
cnt++; |
|
16 |
#endif |
|
17 |
|
|
18 |
return 0; |
|
19 |
} |
|
20 |
|
|
21 |
void (mouse_ih)(void){ |
|
22 |
uint8_t status_reg; |
|
23 |
|
|
24 |
if(util_sys_inb(STATUS_REG,&status_reg)!=0){ //checks if there is an error |
|
25 |
printf("Error reading status register in the keyboard interruption\n"); |
|
26 |
return; |
|
27 |
} |
|
28 |
if(((status_reg & STAT_REG_OBF)==0) ||((status_reg&(STAT_REG_PAR|STAT_REG_TIMEOUT))!=0)){ //checks if there is a parity or timeout error (mask -> 0xC0, bit 7 and 6 set), checks if output buffer is empty |
|
29 |
printf("Parity/Timeout error or output buffer is empty or data coming from the mouse\n"); |
|
30 |
return; |
|
31 |
} |
|
32 |
if(util_sys_inb(OUTPUT_BUF,&byte)!=0){//checks if there is an error |
|
33 |
printf("Error reading output buffer in the keyboard interruption\n"); |
|
34 |
return; |
|
35 |
} |
|
36 |
|
|
37 |
} |
|
38 |
|
|
39 |
int (mouse_subscribe_int)(uint8_t *bit_no) { //similar function to that of timer_subscribe_int |
|
40 |
*bit_no = BIT(keyboard_id); |
|
41 |
if(sys_irqsetpolicy(KEYBOARD_IRQ,(IRQ_REENABLE|IRQ_EXCLUSIVE),&keyboard_id)==1){ //operation to subscribe int |
|
42 |
printf("Error subscribing int\n"); |
|
43 |
return 1; |
|
44 |
} |
|
45 |
return 0; |
|
46 |
} |
|
47 |
|
|
48 |
int (mouse_unsubscribe_int)() { //similar function to that of timer_unsubscribe_int |
|
49 |
if(sys_irqrmpolicy(&keyboard_id)==1){ |
|
50 |
printf("Error unsubscribing int\n"); |
|
51 |
return 1; |
|
52 |
} |
|
53 |
return 0; |
|
54 |
} |
|
55 |
|
|
56 |
int parse_packet(struct packet *pp){ |
|
57 |
if((pp->bytes[0]&0x80) == 0x80){ |
|
58 |
pp->y_ov=true; |
|
59 |
|
|
60 |
} |
|
61 |
else{ |
|
62 |
pp->y_ov=false; |
|
63 |
} |
|
64 |
|
|
65 |
if((pp->bytes[0]&0x40)==0x40){ |
|
66 |
pp->x_ov=true; |
|
67 |
|
|
68 |
} |
|
69 |
else{ |
|
70 |
pp->x_ov=false; |
|
71 |
} |
|
72 |
|
|
73 |
if((pp->bytes[0]&0x02)==0x02){ |
|
74 |
pp->rb=true; |
|
75 |
|
|
76 |
} |
|
77 |
else{ |
|
78 |
pp->rb=false; |
|
79 |
} |
|
80 |
|
|
81 |
if((pp->bytes[0]&0x04)==0x04){ |
|
82 |
pp->mb=true; |
|
83 |
} |
|
84 |
else{ |
|
85 |
pp->mb=false; |
|
86 |
} |
|
87 |
|
|
88 |
if((pp->bytes[0]&0x01)==0x01){ |
|
89 |
pp->lb=true; |
|
90 |
} |
|
91 |
else{ |
|
92 |
pp->lb=false; |
|
93 |
} |
|
94 |
|
|
95 |
if((pp->bytes[0]&0x20)==0x20){ //it means y_delta is negative |
|
96 |
pp->delta_y=~pp->bytes[2]; |
|
97 |
pp->delta_y+=1; |
|
98 |
|
|
99 |
} |
|
100 |
else{ |
|
101 |
pp->delta_y=pp->bytes[2]; |
|
102 |
} |
|
103 |
|
|
104 |
if((pp->bytes[0]&0x10)==0x10){ //it means x_delta is negative |
|
105 |
pp->delta_x=~pp->bytes[1]; |
|
106 |
pp->delta_x+=1; |
|
107 |
|
|
108 |
} |
|
109 |
else{ |
|
110 |
pp->delta_y=pp->bytes[1]; |
|
111 |
} |
|
112 |
} |
lab4/mouse.h | ||
---|---|---|
1 |
#ifndef _MOUSE_H |
|
2 |
#define _MOUSE_H |
|
3 |
|
|
4 |
#include <lcom/lcf.h> |
|
5 |
#include <stdbool.h> |
|
6 |
#include <stdint.h> |
|
7 |
#include <minix/syslib.h> |
|
8 |
#include <minix/sysutil.h> |
|
9 |
|
|
10 |
#include "i8042.h" |
|
11 |
|
|
12 |
/** |
|
13 |
* @brief Handles mouse interrupts |
|
14 |
* |
|
15 |
* Reads the status register, the output buffer and the mouse data |
|
16 |
* If there was some error, the byte read from the OB should be discarded |
|
17 |
* |
|
18 |
* All communication with other code must be done via global variables, static if possible |
|
19 |
* |
|
20 |
* Must be defined using parenthesis around the function name: |
|
21 |
*/ |
|
22 |
void (mouse_ih)(void); |
|
23 |
/** |
|
24 |
* @brief Invokes sys_inb() system call but reads the value into a uint8_t variable. |
|
25 |
* |
|
26 |
* @param port the input port that is to be read |
|
27 |
* @param value address of 8-bit variable to be update with the value read |
|
28 |
* @return Return 0 upon success and non-zero otherwise |
|
29 |
*/ |
|
30 |
int (util_sys_inb)(int port, uint8_t *value); |
|
31 |
/** |
|
32 |
* @brief Subscribes and enables mouse interrupts |
|
33 |
* |
|
34 |
* @param bit_no address of memory to be initialized with the bit number to be set in the mask returned upon an interrupt |
|
35 |
* @return Return 0 upon success and non-zero otherwise |
|
36 |
*/ |
|
37 |
int(mouse_subscribe_int)(uint8_t *bit_no); |
|
38 |
|
|
39 |
/** |
|
40 |
* @brief Unsubscribes mouse interrupts |
|
41 |
* |
|
42 |
* @return Return 0 upon success and non-zero otherwise |
|
43 |
*/ |
|
44 |
int(mouse_unsubscribe_int)(); |
|
45 |
/** |
|
46 |
* |
|
47 |
* |
|
48 |
* |
|
49 |
*/ |
|
50 |
int(parse_packet)(struct packet *pp); |
Also available in: Unified diff