Project

General

Profile

Statistics
| Revision:

root / lab4 / mouse.c @ 78

History | View | Annotate | Download (3.88 KB)

1
#include <lcom/lcf.h>
2

    
3
#include "mouse.h"
4

    
5
#include "errors.h"
6
#include "kbc_macros.h"
7
#include "mouse_macros.h"
8
#include "kbc.h"
9

    
10
int (subscribe_mouse_interrupt)(uint8_t interrupt_bit, int *interrupt_id) {
11
    if (interrupt_id == NULL) return NULL_PTR;
12
    *interrupt_id = interrupt_bit;
13
    if (sys_irqsetpolicy(MOUSE_IRQ, IRQ_REENABLE | IRQ_EXCLUSIVE, interrupt_id)) return SBCR_ERROR;
14
    return SUCCESS;
15
}
16

    
17
int got_error_mouse_ih = 0;
18
uint8_t packet[3];
19
int counter = 0;
20

    
21
void (mouse_ih)(void) {
22
    uint8_t status = 0;
23
    got_error_mouse_ih = 0;
24
    if(counter >= 3) counter = 0;
25

    
26
    if ((got_error_mouse_ih = util_sys_inb(STATUS_REG, &status))) return;
27

    
28
    if (status & (TIME_OUT_REC | PARITY_ERROR)) {
29
        got_error_mouse_ih = OTHER_ERROR;
30
        return;
31
    }
32
    if (((status & AUX_MOUSE) == 0) || ((status & OUT_BUF_FUL) == 0)) {
33
        got_error_mouse_ih = OTHER_ERROR;
34
        return;
35
    }
36

    
37
    uint8_t byte = 0;
38

    
39
    if ((got_error_mouse_ih = util_sys_inb(OUTPUT_BUF, &byte))) return;
40

    
41
    /// This does not run if: I was expecting the first one but what I get is definitely not the first byte
42
    if((byte & FIRST_BYTE_ID)  || counter){
43
        packet[counter] = byte;
44
        counter++;
45
    }
46
}
47

    
48
struct packet (mouse_parse_packet)(const uint8_t *packet_bytes){
49
    struct packet pp;
50
    pp.bytes[0] = packet_bytes[0];
51
    pp.bytes[1] = packet_bytes[1];
52
    pp.bytes[2] = packet_bytes[2];
53
    pp.rb       = pp.bytes[0] & RIGHT_BUTTON;
54
    pp.mb       = pp.bytes[0] & MIDDLE_BUTTON;
55
    pp.lb       = pp.bytes[0] & LEFT_BUTTON;
56
    pp.delta_x  = sign_extend_byte((packet_bytes[0] & MSB_X_DELTA) != 0, pp.bytes[1]);
57
    pp.delta_y  = sign_extend_byte((packet_bytes[0] & MSB_Y_DELTA) != 0, pp.bytes[2]);
58
    pp.x_ov     = pp.bytes[0] & X_OVERFLOW;
59
    pp.y_ov     = pp.bytes[0] & Y_OVERFLOW;
60
    return pp;
61
}
62

    
63
int (mouse_set_data_report)(int on){
64
    int ret = 0;
65
    if(on){
66
        if((ret = mouse_issue_cmd(ENABLE_DATA_REP))) return ret;
67
    }
68
    else{
69
        if((ret = mouse_issue_cmd(   DIS_DATA_REP))) return ret;
70
    }
71
    return ret;
72
}
73

    
74
int (mouse_read_data)(uint8_t *data) {
75
    int ret;
76
    if ((ret = mouse_issue_cmd(READ_DATA))) return ret;
77
    if ((ret = mouse_read_byte(data))) return ret;
78
    return SUCCESS;
79
}
80

    
81
int (mouse_issue_cmd)(uint32_t cmd) {
82
    int ret;
83
    uint8_t ack = 0;
84
    for (unsigned int i = 0; i < KBC_NUM_TRIES; i++) {
85
        if ((ret = kbc_issue_cmd(MOUSE_WRITE_B))) return ret;
86
        if ((ret = kbc_issue_arg(cmd))) return ret;
87
        if ((ret = mouse_read_ack(&ack))) return ret;
88

    
89
        if (ack == ACK_OK) return SUCCESS;
90
        if (ack == ACK_ERROR) return INVALID_COMMAND;
91
        tickdelay(micros_to_ticks(DELAY));
92
    }
93
    return TIMEOUT_ERROR;
94
}
95

    
96
int (mouse_read_byte)(uint8_t *byte) {
97
    int ret = 0;
98
    uint8_t stat;
99
    for(int i = 0; i < KBC_NUM_TRIES; ++i){
100
        if((ret = util_sys_inb(STATUS_REG, &stat))) return ret;
101
        if((stat&OUT_BUF_FUL) && (stat&AUX_MOUSE)) {
102
            if(stat & (PARITY_ERROR | TIME_OUT_REC)) return OTHER_ERROR;
103
            if((ret = util_sys_inb(OUTPUT_BUF, byte))) return ret;
104
            else return SUCCESS;
105
        }
106
        tickdelay(micros_to_ticks(DELAY));
107
    }
108
    return TIMEOUT_ERROR;
109
}
110

    
111
int (mouse_read_ack)(uint8_t *byte) {
112
    int ret = 0;
113
    uint8_t stat;
114
    //for(int i = 0; i < KBC_NUM_TRIES; ++i){
115
        if((ret = util_sys_inb(STATUS_REG, &stat))) return ret;
116
        //if((stat&OUT_BUF_FUL) && (stat&AUX_MOUSE)) {
117
            if(stat & (PARITY_ERROR | TIME_OUT_REC)) return OTHER_ERROR;
118
            if((ret = util_sys_inb(OUTPUT_BUF, byte))) return ret;
119
            else return SUCCESS;
120
        //}
121
        //tickdelay(micros_to_ticks(DELAY));
122
    //}
123
    //return TIMEOUT_ERROR;
124
}
125

    
126
int16_t (sign_extend_byte)(uint8_t sign_bit, uint8_t byte) {
127
    return (int16_t)(((0xFF * sign_bit)<<8) | byte);
128
}