summaryrefslogtreecommitdiff
path: root/cesar/test_general/ecos/src/pci_int.c
blob: c547c2e120538ded7a2c2fe13493cbfc5245a11a (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
/* Cesar project {{{
 *
 * Copyright (C) 2008 Spidcom
 *
 * <<<Licence>>>
 *
 * }}} */
/**
 * \file    pci_int.c
 * \brief   « brief description »
 * \ingroup « module »
 *
 * « long description »
 */

#include <cyg/kernel/kapi.h>
#include <cyg/hal/drv_api.h>
#include <cyg/infra/diag.h>

//
// Local defines
//
#define MY_THREAD_STACK_SIZE    (4096 / sizeof(int))
#define CYGNUM_HAL_PRI_HIGH     0
#define PCI_INT                 CYGNUM_HAL_INTERRUPT_5

//
// Static variables
//
static int my_thread_stack[MY_THREAD_STACK_SIZE];
static cyg_handle_t my_thread_handle;
static cyg_thread my_thread_obj;

static cyg_interrupt intpci;
static cyg_handle_t intpci_handle;
static cyg_sem_t data_ready;

//
// Thread.
//
void my_thread(cyg_addrword_t index)
{
    while(1)
    {
        diag_write_string("Waiting pci_handler semaphore...\n");
        // Wait semaphore
        cyg_semaphore_wait(&data_ready);
        diag_write_string("Thank you PCI DSR, I will continue\n\n");
    }
}

//
// Interrupt service routine for interrupt pci.
//
cyg_uint32 interrupt_pci_isr(
    cyg_vector_t vector,
    cyg_addrword_t data)
{
    // Block this interrupt from occurring until
    // the DSR completes.
    cyg_drv_interrupt_mask(vector);

    // Tell the processor that we have received
    // the interrupt.
    cyg_drv_interrupt_acknowledge(vector);

    diag_write_char('i');
    // Tell the kernel that chained interrupt processing
    // is done and the DSR needs to be executed next.
    return CYG_ISR_CALL_DSR;
}

//
// Deferred service routine for interrupt pci.
//
void interrupt_pci_dsr(
    cyg_vector_t vector,
    cyg_ucount32 count,
    cyg_addrword_t data)
{
    // Signal the thread to run for further processing.
    cyg_semaphore_post(&data_ready);

    // Allow this interrupt to occur again.
    cyg_drv_interrupt_unmask(vector);
}

//
// Main.
//
void cyg_user_start(void)
{
    cyg_vector_t intpci_vector = PCI_INT;
    cyg_priority_t intpci_priority = CYGNUM_HAL_PRI_HIGH;


    // Thread Creation
    cyg_thread_create(12, my_thread, (cyg_addrword_t) 0,
                      "My Thread", &my_thread_stack, MY_THREAD_STACK_SIZE,
                      &my_thread_handle, &my_thread_obj);


    // Initialize the semaphore used for interrupt pci.
    cyg_semaphore_init(&data_ready, 0);

    // Create interrupt pci
    cyg_drv_interrupt_create(
        intpci_vector,
        intpci_priority,
        0,
        &interrupt_pci_isr,
        &interrupt_pci_dsr,
        &intpci_handle,
        &intpci);

    // Attach the interrupt created to the vector.
    cyg_drv_interrupt_attach(intpci_handle);

    // Unmask the interrupt we just configured.
    diag_write_string("Unmasking Interrupts....\n");
    cyg_drv_interrupt_unmask(intpci_vector);

    // Starting Thread
    diag_write_string("Starting Thread....\n\n");
    cyg_thread_resume(my_thread_handle);

    // Starting Scheduler for Thread and DSR
    cyg_scheduler_start();
}