1 /*
2  * Copyright (c) 2006-2021, RT-Thread Development Team
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  *
6  * Change Logs:
7  * Date           Author        Notes
8  * 2011-01-13     weety     first version
9  */
10 
11 #include <rtthread.h>
12 #include "gpio.h"
13 
14 #define GPIO0_BASE          (DAVINCI_GPIO_BASE + 0x10)
15 #define GPIO1_BASE          (DAVINCI_GPIO_BASE + 0x38)
16 #define GPIO2_BASE          (DAVINCI_GPIO_BASE + 0x60)
17 #define GPIO3_BASE          (DAVINCI_GPIO_BASE + 0x88)
18 
19 
20 static unsigned int dm365_gpio_base = (unsigned int)GPIO0_BASE;
21 
22 #define GPIO_OE         (dm365_gpio_base + 0x00)
23 #define GPIO_DATAIN     (dm365_gpio_base + 0x10)
24 #define GPIO_DATAOUT        (dm365_gpio_base + 0x04)
25 #define GPIO_CLROUT     (dm365_gpio_base + 0x0C)
26 #define GPIO_SETOUT     (dm365_gpio_base + 0x08)
27 
28 #define gpio_dirin(n)       *(volatile unsigned int *)((GPIO_OE)) |= 1<<(n)
29 #define gpio_dirout(n)  *(volatile unsigned int *)((GPIO_OE)) &= ~(1u<<(n))
30 #define gpio_set(n)     *(volatile unsigned int *)((GPIO_SETOUT)) = 1<<(n)
31 #define gpio_clr(n)     *(volatile unsigned int *)((GPIO_CLROUT)) = 1<<(n)
32 #define gpio_get(n)     ( ( *(volatile unsigned int *)((GPIO_DATAIN)) & (1<<(n)) ) ? 1 : 0 )
33 
34  #define GPIO_GRP_MASK (5)
35 
gpio_to_base(unsigned int gpio)36 static int gpio_to_base(unsigned int gpio)
37 {
38     unsigned int grp_idx;
39     int ret;
40 
41     grp_idx = gpio >> GPIO_GRP_MASK;
42 
43     switch (grp_idx) {
44         case 0:
45             dm365_gpio_base = (unsigned int)GPIO0_BASE;
46             ret = 0;
47             break;
48         case 1:
49             dm365_gpio_base = (unsigned int)GPIO1_BASE;
50             ret = 0;
51             break;
52         case 2:
53             dm365_gpio_base = (unsigned int)GPIO2_BASE;
54             ret = 0;
55             break;
56         case 3:
57             dm365_gpio_base = (unsigned int)GPIO3_BASE;
58             ret = 0;
59             break;
60         default:
61             ret =-RT_EIO;
62             break;
63     }
64     return ret;
65 }
66 
67 
gpio_direction_input(unsigned int gpio)68 int gpio_direction_input(unsigned int gpio)
69 {
70     unsigned int offset;
71     int ret=0;
72 
73     rt_ubase_t temp = rt_hw_interrupt_disable();
74     ret = gpio_to_base(gpio);
75     if (ret < 0) {
76         goto gpio_free;
77     }
78     offset =  gpio & ((1 << GPIO_GRP_MASK) -1);
79 
80     gpio_dirin(offset);
81 
82 gpio_free:
83     rt_hw_interrupt_enable(temp);
84 
85     return ret;
86 }
87 
gpio_direction_output(unsigned int gpio,int value)88 int gpio_direction_output(unsigned int gpio, int value)
89 {
90     unsigned int offset;
91     int ret=0;
92 
93     rt_ubase_t temp = rt_hw_interrupt_disable();
94     ret = gpio_to_base(gpio);
95     if (ret < 0) {
96         goto gpio_free;
97     }
98 
99     offset =  gpio & ((1 << GPIO_GRP_MASK) -1);
100 
101     if (value) {
102         gpio_set(offset);
103     }
104     else {
105         gpio_clr(offset);
106     }
107 
108     gpio_dirout(offset);
109 
110 gpio_free:
111     rt_hw_interrupt_enable(temp);
112 
113     return ret;
114 }
115 
gpio_set_value(unsigned int gpio,int value)116 int  gpio_set_value(unsigned int gpio, int value)
117 {
118     unsigned int offset;
119     int ret=0;
120 
121     rt_ubase_t temp = rt_hw_interrupt_disable();
122     ret = gpio_to_base(gpio);
123     if (ret < 0) {
124         goto gpio_free;
125     }
126 
127     offset =  gpio & ((1 << GPIO_GRP_MASK) -1);
128 
129     if (value) {
130         gpio_set(offset);
131     }
132     else {
133         gpio_clr(offset);
134     }
135 
136 gpio_free:
137     rt_hw_interrupt_enable(temp);
138 
139     return ret;
140 }
141 
gpio_get_value(unsigned int gpio)142 int gpio_get_value(unsigned int gpio)
143 {
144     unsigned int offset;
145     int ret=0;
146 
147     rt_ubase_t temp = rt_hw_interrupt_disable();
148     ret = gpio_to_base(gpio);
149     if (ret < 0) {
150         goto gpio_free;
151     }
152 
153     offset =  gpio & ((1 << GPIO_GRP_MASK) -1);
154     ret = gpio_get(offset);
155 
156 gpio_free:
157     rt_hw_interrupt_enable(temp);
158 
159     return ret;
160 }
161 
162 
163