• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2003, Axis Communications AB.
3  */
4 
5 #include <linux/console.h>
6 #include <linux/init.h>
7 #include <hwregs/reg_rdwr.h>
8 #include <hwregs/reg_map.h>
9 #include <hwregs/ser_defs.h>
10 #include <hwregs/dma_defs.h>
11 #include <mach/pinmux.h>
12 
13 struct dbg_port
14 {
15 	unsigned char nbr;
16 	unsigned long instance;
17 	unsigned int started;
18 	unsigned long baudrate;
19 	unsigned char parity;
20 	unsigned int bits;
21 };
22 
23 struct dbg_port ports[] =
24 {
25   {
26     0,
27     regi_ser0,
28     0,
29     115200,
30     'N',
31     8
32   },
33   {
34     1,
35     regi_ser1,
36     0,
37     115200,
38     'N',
39     8
40   },
41   {
42     2,
43     regi_ser2,
44     0,
45     115200,
46     'N',
47     8
48   },
49   {
50     3,
51     regi_ser3,
52     0,
53     115200,
54     'N',
55     8
56   },
57 #if CONFIG_ETRAX_SERIAL_PORTS == 5
58   {
59     4,
60     regi_ser4,
61     0,
62     115200,
63     'N',
64     8
65   },
66 #endif
67 };
68 static struct dbg_port *port =
69 #if defined(CONFIG_ETRAX_DEBUG_PORT0)
70 	&ports[0];
71 #elif defined(CONFIG_ETRAX_DEBUG_PORT1)
72 	&ports[1];
73 #elif defined(CONFIG_ETRAX_DEBUG_PORT2)
74 	&ports[2];
75 #elif defined(CONFIG_ETRAX_DEBUG_PORT3)
76 	&ports[3];
77 #elif defined(CONFIG_ETRAX_DEBUG_PORT4)
78 	&ports[4];
79 #else
80 	NULL;
81 #endif
82 
83 #ifdef CONFIG_ETRAX_KGDB
84 static struct dbg_port *kgdb_port =
85 #if defined(CONFIG_ETRAX_KGDB_PORT0)
86 	&ports[0];
87 #elif defined(CONFIG_ETRAX_KGDB_PORT1)
88 	&ports[1];
89 #elif defined(CONFIG_ETRAX_KGDB_PORT2)
90 	&ports[2];
91 #elif defined(CONFIG_ETRAX_KGDB_PORT3)
92 	&ports[3];
93 #elif defined(CONFIG_ETRAX_KGDB_PORT4)
94 	&ports[4];
95 #else
96 	NULL;
97 #endif
98 #endif
99 
100 static void
start_port(struct dbg_port * p)101 start_port(struct dbg_port* p)
102 {
103 	if (!p)
104 		return;
105 
106 	if (p->started)
107 		return;
108 	p->started = 1;
109 
110 	if (p->nbr == 1)
111 		crisv32_pinmux_alloc_fixed(pinmux_ser1);
112 	else if (p->nbr == 2)
113 		crisv32_pinmux_alloc_fixed(pinmux_ser2);
114 	else if (p->nbr == 3)
115 		crisv32_pinmux_alloc_fixed(pinmux_ser3);
116 #if CONFIG_ETRAX_SERIAL_PORTS == 5
117 	else if (p->nbr == 4)
118 		crisv32_pinmux_alloc_fixed(pinmux_ser4);
119 #endif
120 
121 	/* Set up serial port registers */
122 	reg_ser_rw_tr_ctrl tr_ctrl = {0};
123 	reg_ser_rw_tr_dma_en tr_dma_en = {0};
124 
125 	reg_ser_rw_rec_ctrl rec_ctrl = {0};
126 	reg_ser_rw_tr_baud_div tr_baud_div = {0};
127 	reg_ser_rw_rec_baud_div rec_baud_div = {0};
128 
129 	tr_ctrl.base_freq = rec_ctrl.base_freq = regk_ser_f29_493;
130 	tr_dma_en.en = rec_ctrl.dma_mode = regk_ser_no;
131 	tr_baud_div.div = rec_baud_div.div = 29493000 / p->baudrate / 8;
132 	tr_ctrl.en = rec_ctrl.en = 1;
133 
134 	if (p->parity == 'O')
135 	{
136 		tr_ctrl.par_en = regk_ser_yes;
137 		tr_ctrl.par = regk_ser_odd;
138 		rec_ctrl.par_en = regk_ser_yes;
139 		rec_ctrl.par = regk_ser_odd;
140 	}
141 	else if (p->parity == 'E')
142 	{
143 		tr_ctrl.par_en = regk_ser_yes;
144 		tr_ctrl.par = regk_ser_even;
145 		rec_ctrl.par_en = regk_ser_yes;
146 		rec_ctrl.par = regk_ser_odd;
147 	}
148 
149 	if (p->bits == 7)
150 	{
151 		tr_ctrl.data_bits = regk_ser_bits7;
152 		rec_ctrl.data_bits = regk_ser_bits7;
153 	}
154 
155 	REG_WR (ser, p->instance, rw_tr_baud_div, tr_baud_div);
156 	REG_WR (ser, p->instance, rw_rec_baud_div, rec_baud_div);
157 	REG_WR (ser, p->instance, rw_tr_dma_en, tr_dma_en);
158 	REG_WR (ser, p->instance, rw_tr_ctrl, tr_ctrl);
159 	REG_WR (ser, p->instance, rw_rec_ctrl, rec_ctrl);
160 }
161 
162 #ifdef CONFIG_ETRAX_KGDB
163 /* Use polling to get a single character from the kernel debug port */
164 int
getDebugChar(void)165 getDebugChar(void)
166 {
167 	reg_ser_rs_stat_din stat;
168 	reg_ser_rw_ack_intr ack_intr = { 0 };
169 
170 	do {
171 		stat = REG_RD(ser, kgdb_port->instance, rs_stat_din);
172 	} while (!stat.dav);
173 
174 	/* Ack the data_avail interrupt. */
175 	ack_intr.dav = 1;
176 	REG_WR(ser, kgdb_port->instance, rw_ack_intr, ack_intr);
177 
178 	return stat.data;
179 }
180 
181 /* Use polling to put a single character to the kernel debug port */
182 void
putDebugChar(int val)183 putDebugChar(int val)
184 {
185 	reg_ser_r_stat_din stat;
186 	do {
187 		stat = REG_RD(ser, kgdb_port->instance, r_stat_din);
188 	} while (!stat.tr_rdy);
189 	REG_WR_INT(ser, kgdb_port->instance, rw_dout, val);
190 }
191 #endif /* CONFIG_ETRAX_KGDB */
192 
193 /* Register console for printk's, etc. */
194 int __init
init_etrax_debug(void)195 init_etrax_debug(void)
196 {
197         start_port(port);
198 
199 #ifdef CONFIG_ETRAX_KGDB
200 	start_port(kgdb_port);
201 #endif /* CONFIG_ETRAX_KGDB */
202 	return 0;
203 }
204