xref: /openbmc/linux/drivers/misc/c2port/core.c (revision b8bb76713ec50df2f11efee386e16f93d51e1076)
1 /*
2  *  Silicon Labs C2 port core Linux support
3  *
4  *  Copyright (c) 2007 Rodolfo Giometti <giometti@linux.it>
5  *  Copyright (c) 2007 Eurotech S.p.A. <info@eurotech.it>
6  *
7  * This program is free software; you can redistribute it and/or modify it
8  * under the terms of the GNU General Public License version 2 as published by
9  * the Free Software Foundation
10  */
11 
12 #include <linux/module.h>
13 #include <linux/init.h>
14 #include <linux/device.h>
15 #include <linux/errno.h>
16 #include <linux/err.h>
17 #include <linux/kernel.h>
18 #include <linux/ctype.h>
19 #include <linux/delay.h>
20 #include <linux/idr.h>
21 #include <linux/sched.h>
22 
23 #include <linux/c2port.h>
24 
25 #define DRIVER_NAME             "c2port"
26 #define DRIVER_VERSION          "0.51.0"
27 
28 static DEFINE_SPINLOCK(c2port_idr_lock);
29 static DEFINE_IDR(c2port_idr);
30 
31 /*
32  * Local variables
33  */
34 
35 static struct class *c2port_class;
36 
37 /*
38  * C2 registers & commands defines
39  */
40 
41 /* C2 registers */
42 #define C2PORT_DEVICEID		0x00
43 #define C2PORT_REVID		0x01
44 #define C2PORT_FPCTL		0x02
45 #define C2PORT_FPDAT		0xB4
46 
47 /* C2 interface commands */
48 #define C2PORT_GET_VERSION	0x01
49 #define C2PORT_DEVICE_ERASE	0x03
50 #define C2PORT_BLOCK_READ	0x06
51 #define C2PORT_BLOCK_WRITE	0x07
52 #define C2PORT_PAGE_ERASE	0x08
53 
54 /* C2 status return codes */
55 #define C2PORT_INVALID_COMMAND	0x00
56 #define C2PORT_COMMAND_FAILED	0x02
57 #define C2PORT_COMMAND_OK	0x0d
58 
59 /*
60  * C2 port low level signal managements
61  */
62 
63 static void c2port_reset(struct c2port_device *dev)
64 {
65 	struct c2port_ops *ops = dev->ops;
66 
67 	/* To reset the device we have to keep clock line low for at least
68 	 * 20us.
69 	 */
70 	local_irq_disable();
71 	ops->c2ck_set(dev, 0);
72 	udelay(25);
73 	ops->c2ck_set(dev, 1);
74 	local_irq_enable();
75 
76 	udelay(1);
77 }
78 
79 static void c2port_strobe_ck(struct c2port_device *dev)
80 {
81 	struct c2port_ops *ops = dev->ops;
82 
83 	/* During hi-low-hi transition we disable local IRQs to avoid
84 	 * interructions since C2 port specification says that it must be
85 	 * shorter than 5us, otherwise the microcontroller may consider
86 	 * it as a reset signal!
87 	 */
88 	local_irq_disable();
89 	ops->c2ck_set(dev, 0);
90 	udelay(1);
91 	ops->c2ck_set(dev, 1);
92 	local_irq_enable();
93 
94 	udelay(1);
95 }
96 
97 /*
98  * C2 port basic functions
99  */
100 
101 static void c2port_write_ar(struct c2port_device *dev, u8 addr)
102 {
103 	struct c2port_ops *ops = dev->ops;
104 	int i;
105 
106 	/* START field */
107 	c2port_strobe_ck(dev);
108 
109 	/* INS field (11b, LSB first) */
110 	ops->c2d_dir(dev, 0);
111 	ops->c2d_set(dev, 1);
112 	c2port_strobe_ck(dev);
113 	ops->c2d_set(dev, 1);
114 	c2port_strobe_ck(dev);
115 
116 	/* ADDRESS field */
117 	for (i = 0; i < 8; i++) {
118 		ops->c2d_set(dev, addr & 0x01);
119 		c2port_strobe_ck(dev);
120 
121 		addr >>= 1;
122 	}
123 
124 	/* STOP field */
125 	ops->c2d_dir(dev, 1);
126 	c2port_strobe_ck(dev);
127 }
128 
129 static int c2port_read_ar(struct c2port_device *dev, u8 *addr)
130 {
131 	struct c2port_ops *ops = dev->ops;
132 	int i;
133 
134 	/* START field */
135 	c2port_strobe_ck(dev);
136 
137 	/* INS field (10b, LSB first) */
138 	ops->c2d_dir(dev, 0);
139 	ops->c2d_set(dev, 0);
140 	c2port_strobe_ck(dev);
141 	ops->c2d_set(dev, 1);
142 	c2port_strobe_ck(dev);
143 
144 	/* ADDRESS field */
145 	ops->c2d_dir(dev, 1);
146 	*addr = 0;
147 	for (i = 0; i < 8; i++) {
148 		*addr >>= 1;	/* shift in 8-bit ADDRESS field LSB first */
149 
150 		c2port_strobe_ck(dev);
151 		if (ops->c2d_get(dev))
152 			*addr |= 0x80;
153 	}
154 
155 	/* STOP field */
156 	c2port_strobe_ck(dev);
157 
158 	return 0;
159 }
160 
161 static int c2port_write_dr(struct c2port_device *dev, u8 data)
162 {
163 	struct c2port_ops *ops = dev->ops;
164 	int timeout, i;
165 
166 	/* START field */
167 	c2port_strobe_ck(dev);
168 
169 	/* INS field (01b, LSB first) */
170 	ops->c2d_dir(dev, 0);
171 	ops->c2d_set(dev, 1);
172 	c2port_strobe_ck(dev);
173 	ops->c2d_set(dev, 0);
174 	c2port_strobe_ck(dev);
175 
176 	/* LENGTH field (00b, LSB first -> 1 byte) */
177 	ops->c2d_set(dev, 0);
178 	c2port_strobe_ck(dev);
179 	ops->c2d_set(dev, 0);
180 	c2port_strobe_ck(dev);
181 
182 	/* DATA field */
183 	for (i = 0; i < 8; i++) {
184 		ops->c2d_set(dev, data & 0x01);
185 		c2port_strobe_ck(dev);
186 
187 		data >>= 1;
188 	}
189 
190 	/* WAIT field */
191 	ops->c2d_dir(dev, 1);
192 	timeout = 20;
193 	do {
194 		c2port_strobe_ck(dev);
195 		if (ops->c2d_get(dev))
196 			break;
197 
198 		udelay(1);
199 	} while (--timeout > 0);
200 	if (timeout == 0)
201 		return -EIO;
202 
203 	/* STOP field */
204 	c2port_strobe_ck(dev);
205 
206 	return 0;
207 }
208 
209 static int c2port_read_dr(struct c2port_device *dev, u8 *data)
210 {
211 	struct c2port_ops *ops = dev->ops;
212 	int timeout, i;
213 
214 	/* START field */
215 	c2port_strobe_ck(dev);
216 
217 	/* INS field (00b, LSB first) */
218 	ops->c2d_dir(dev, 0);
219 	ops->c2d_set(dev, 0);
220 	c2port_strobe_ck(dev);
221 	ops->c2d_set(dev, 0);
222 	c2port_strobe_ck(dev);
223 
224 	/* LENGTH field (00b, LSB first -> 1 byte) */
225 	ops->c2d_set(dev, 0);
226 	c2port_strobe_ck(dev);
227 	ops->c2d_set(dev, 0);
228 	c2port_strobe_ck(dev);
229 
230 	/* WAIT field */
231 	ops->c2d_dir(dev, 1);
232 	timeout = 20;
233 	do {
234 		c2port_strobe_ck(dev);
235 		if (ops->c2d_get(dev))
236 			break;
237 
238 		udelay(1);
239 	} while (--timeout > 0);
240 	if (timeout == 0)
241 		return -EIO;
242 
243 	/* DATA field */
244 	*data = 0;
245 	for (i = 0; i < 8; i++) {
246 		*data >>= 1;	/* shift in 8-bit DATA field LSB first */
247 
248 		c2port_strobe_ck(dev);
249 		if (ops->c2d_get(dev))
250 			*data |= 0x80;
251 	}
252 
253 	/* STOP field */
254 	c2port_strobe_ck(dev);
255 
256 	return 0;
257 }
258 
259 static int c2port_poll_in_busy(struct c2port_device *dev)
260 {
261 	u8 addr;
262 	int ret, timeout = 20;
263 
264 	do {
265 		ret = (c2port_read_ar(dev, &addr));
266 		if (ret < 0)
267 			return -EIO;
268 
269 		if (!(addr & 0x02))
270 			break;
271 
272 		udelay(1);
273 	} while (--timeout > 0);
274 	if (timeout == 0)
275 		return -EIO;
276 
277 	return 0;
278 }
279 
280 static int c2port_poll_out_ready(struct c2port_device *dev)
281 {
282 	u8 addr;
283 	int ret, timeout = 10000; /* erase flash needs long time... */
284 
285 	do {
286 		ret = (c2port_read_ar(dev, &addr));
287 		if (ret < 0)
288 			return -EIO;
289 
290 		if (addr & 0x01)
291 			break;
292 
293 		udelay(1);
294 	} while (--timeout > 0);
295 	if (timeout == 0)
296 		return -EIO;
297 
298 	return 0;
299 }
300 
301 /*
302  * sysfs methods
303  */
304 
305 static ssize_t c2port_show_name(struct device *dev,
306 				struct device_attribute *attr, char *buf)
307 {
308 	struct c2port_device *c2dev = dev_get_drvdata(dev);
309 
310 	return sprintf(buf, "%s\n", c2dev->name);
311 }
312 
313 static ssize_t c2port_show_flash_blocks_num(struct device *dev,
314 				struct device_attribute *attr, char *buf)
315 {
316 	struct c2port_device *c2dev = dev_get_drvdata(dev);
317 	struct c2port_ops *ops = c2dev->ops;
318 
319 	return sprintf(buf, "%d\n", ops->blocks_num);
320 }
321 
322 static ssize_t c2port_show_flash_block_size(struct device *dev,
323 				struct device_attribute *attr, char *buf)
324 {
325 	struct c2port_device *c2dev = dev_get_drvdata(dev);
326 	struct c2port_ops *ops = c2dev->ops;
327 
328 	return sprintf(buf, "%d\n", ops->block_size);
329 }
330 
331 static ssize_t c2port_show_flash_size(struct device *dev,
332 				struct device_attribute *attr, char *buf)
333 {
334 	struct c2port_device *c2dev = dev_get_drvdata(dev);
335 	struct c2port_ops *ops = c2dev->ops;
336 
337 	return sprintf(buf, "%d\n", ops->blocks_num * ops->block_size);
338 }
339 
340 static ssize_t c2port_show_access(struct device *dev,
341 				struct device_attribute *attr, char *buf)
342 {
343 	struct c2port_device *c2dev = dev_get_drvdata(dev);
344 
345 	return sprintf(buf, "%d\n", c2dev->access);
346 }
347 
348 static ssize_t c2port_store_access(struct device *dev,
349 				struct device_attribute *attr,
350 				const char *buf, size_t count)
351 {
352 	struct c2port_device *c2dev = dev_get_drvdata(dev);
353 	struct c2port_ops *ops = c2dev->ops;
354 	int status, ret;
355 
356 	ret = sscanf(buf, "%d", &status);
357 	if (ret != 1)
358 		return -EINVAL;
359 
360 	mutex_lock(&c2dev->mutex);
361 
362 	c2dev->access = !!status;
363 
364 	/* If access is "on" clock should be HIGH _before_ setting the line
365 	 * as output and data line should be set as INPUT anyway */
366 	if (c2dev->access)
367 		ops->c2ck_set(c2dev, 1);
368 	ops->access(c2dev, c2dev->access);
369 	if (c2dev->access)
370 		ops->c2d_dir(c2dev, 1);
371 
372 	mutex_unlock(&c2dev->mutex);
373 
374 	return count;
375 }
376 
377 static ssize_t c2port_store_reset(struct device *dev,
378 				struct device_attribute *attr,
379 				const char *buf, size_t count)
380 {
381 	struct c2port_device *c2dev = dev_get_drvdata(dev);
382 
383 	/* Check the device access status */
384 	if (!c2dev->access)
385 		return -EBUSY;
386 
387 	mutex_lock(&c2dev->mutex);
388 
389 	c2port_reset(c2dev);
390 	c2dev->flash_access = 0;
391 
392 	mutex_unlock(&c2dev->mutex);
393 
394 	return count;
395 }
396 
397 static ssize_t __c2port_show_dev_id(struct c2port_device *dev, char *buf)
398 {
399 	u8 data;
400 	int ret;
401 
402 	/* Select DEVICEID register for C2 data register accesses */
403 	c2port_write_ar(dev, C2PORT_DEVICEID);
404 
405 	/* Read and return the device ID register */
406 	ret = c2port_read_dr(dev, &data);
407 	if (ret < 0)
408 		return ret;
409 
410 	return sprintf(buf, "%d\n", data);
411 }
412 
413 static ssize_t c2port_show_dev_id(struct device *dev,
414 				struct device_attribute *attr, char *buf)
415 {
416 	struct c2port_device *c2dev = dev_get_drvdata(dev);
417 	ssize_t ret;
418 
419 	/* Check the device access status */
420 	if (!c2dev->access)
421 		return -EBUSY;
422 
423 	mutex_lock(&c2dev->mutex);
424 	ret = __c2port_show_dev_id(c2dev, buf);
425 	mutex_unlock(&c2dev->mutex);
426 
427 	if (ret < 0)
428 		dev_err(dev, "cannot read from %s\n", c2dev->name);
429 
430 	return ret;
431 }
432 
433 static ssize_t __c2port_show_rev_id(struct c2port_device *dev, char *buf)
434 {
435 	u8 data;
436 	int ret;
437 
438 	/* Select REVID register for C2 data register accesses */
439 	c2port_write_ar(dev, C2PORT_REVID);
440 
441 	/* Read and return the revision ID register */
442 	ret = c2port_read_dr(dev, &data);
443 	if (ret < 0)
444 		return ret;
445 
446 	return sprintf(buf, "%d\n", data);
447 }
448 
449 static ssize_t c2port_show_rev_id(struct device *dev,
450 				struct device_attribute *attr, char *buf)
451 {
452 	struct c2port_device *c2dev = dev_get_drvdata(dev);
453 	ssize_t ret;
454 
455 	/* Check the device access status */
456 	if (!c2dev->access)
457 		return -EBUSY;
458 
459 	mutex_lock(&c2dev->mutex);
460 	ret = __c2port_show_rev_id(c2dev, buf);
461 	mutex_unlock(&c2dev->mutex);
462 
463 	if (ret < 0)
464 		dev_err(c2dev->dev, "cannot read from %s\n", c2dev->name);
465 
466 	return ret;
467 }
468 
469 static ssize_t c2port_show_flash_access(struct device *dev,
470 				struct device_attribute *attr, char *buf)
471 {
472 	struct c2port_device *c2dev = dev_get_drvdata(dev);
473 
474 	return sprintf(buf, "%d\n", c2dev->flash_access);
475 }
476 
477 static ssize_t __c2port_store_flash_access(struct c2port_device *dev,
478 						int status)
479 {
480 	int ret;
481 
482 	/* Check the device access status */
483 	if (!dev->access)
484 		return -EBUSY;
485 
486 	dev->flash_access = !!status;
487 
488 	/* If flash_access is off we have nothing to do... */
489 	if (dev->flash_access == 0)
490 		return 0;
491 
492 	/* Target the C2 flash programming control register for C2 data
493 	 * register access */
494 	c2port_write_ar(dev, C2PORT_FPCTL);
495 
496 	/* Write the first keycode to enable C2 Flash programming */
497 	ret = c2port_write_dr(dev, 0x02);
498 	if (ret < 0)
499 		return ret;
500 
501 	/* Write the second keycode to enable C2 Flash programming */
502 	ret = c2port_write_dr(dev, 0x01);
503 	if (ret < 0)
504 		return ret;
505 
506 	/* Delay for at least 20ms to ensure the target is ready for
507 	 * C2 flash programming */
508 	mdelay(25);
509 
510 	return 0;
511 }
512 
513 static ssize_t c2port_store_flash_access(struct device *dev,
514 				struct device_attribute *attr,
515 				const char *buf, size_t count)
516 {
517 	struct c2port_device *c2dev = dev_get_drvdata(dev);
518 	int status;
519 	ssize_t ret;
520 
521 	ret = sscanf(buf, "%d", &status);
522 	if (ret != 1)
523 		return -EINVAL;
524 
525 	mutex_lock(&c2dev->mutex);
526 	ret = __c2port_store_flash_access(c2dev, status);
527 	mutex_unlock(&c2dev->mutex);
528 
529 	if (ret < 0) {
530 		dev_err(c2dev->dev, "cannot enable %s flash programming\n",
531 			c2dev->name);
532 		return ret;
533 	}
534 
535 	return count;
536 }
537 
538 static ssize_t __c2port_write_flash_erase(struct c2port_device *dev)
539 {
540 	u8 status;
541 	int ret;
542 
543 	/* Target the C2 flash programming data register for C2 data register
544 	 * access.
545 	 */
546 	c2port_write_ar(dev, C2PORT_FPDAT);
547 
548 	/* Send device erase command */
549 	c2port_write_dr(dev, C2PORT_DEVICE_ERASE);
550 
551 	/* Wait for input acknowledge */
552 	ret = c2port_poll_in_busy(dev);
553 	if (ret < 0)
554 		return ret;
555 
556 	/* Should check status before starting FLASH access sequence */
557 
558 	/* Wait for status information */
559 	ret = c2port_poll_out_ready(dev);
560 	if (ret < 0)
561 		return ret;
562 
563 	/* Read flash programming interface status */
564 	ret = c2port_read_dr(dev, &status);
565 	if (ret < 0)
566 		return ret;
567 	if (status != C2PORT_COMMAND_OK)
568 		return -EBUSY;
569 
570 	/* Send a three-byte arming sequence to enable the device erase.
571 	 * If the sequence is not received correctly, the command will be
572 	 * ignored.
573 	 * Sequence is: 0xde, 0xad, 0xa5.
574 	 */
575 	c2port_write_dr(dev, 0xde);
576 	ret = c2port_poll_in_busy(dev);
577 	if (ret < 0)
578 		return ret;
579 	c2port_write_dr(dev, 0xad);
580 	ret = c2port_poll_in_busy(dev);
581 	if (ret < 0)
582 		return ret;
583 	c2port_write_dr(dev, 0xa5);
584 	ret = c2port_poll_in_busy(dev);
585 	if (ret < 0)
586 		return ret;
587 
588 	ret = c2port_poll_out_ready(dev);
589 	if (ret < 0)
590 		return ret;
591 
592 	return 0;
593 }
594 
595 static ssize_t c2port_store_flash_erase(struct device *dev,
596 				struct device_attribute *attr,
597 				const char *buf, size_t count)
598 {
599 	struct c2port_device *c2dev = dev_get_drvdata(dev);
600 	int ret;
601 
602 	/* Check the device and flash access status */
603 	if (!c2dev->access || !c2dev->flash_access)
604 		return -EBUSY;
605 
606 	mutex_lock(&c2dev->mutex);
607 	ret = __c2port_write_flash_erase(c2dev);
608 	mutex_unlock(&c2dev->mutex);
609 
610 	if (ret < 0) {
611 		dev_err(c2dev->dev, "cannot erase %s flash\n", c2dev->name);
612 		return ret;
613 	}
614 
615 	return count;
616 }
617 
618 static ssize_t __c2port_read_flash_data(struct c2port_device *dev,
619 				char *buffer, loff_t offset, size_t count)
620 {
621 	struct c2port_ops *ops = dev->ops;
622 	u8 status, nread = 128;
623 	int i, ret;
624 
625 	/* Check for flash end */
626 	if (offset >= ops->block_size * ops->blocks_num)
627 		return 0;
628 
629 	if (ops->block_size * ops->blocks_num - offset < nread)
630 		nread = ops->block_size * ops->blocks_num - offset;
631 	if (count < nread)
632 		nread = count;
633 	if (nread == 0)
634 		return nread;
635 
636 	/* Target the C2 flash programming data register for C2 data register
637 	 * access */
638 	c2port_write_ar(dev, C2PORT_FPDAT);
639 
640 	/* Send flash block read command */
641 	c2port_write_dr(dev, C2PORT_BLOCK_READ);
642 
643 	/* Wait for input acknowledge */
644 	ret = c2port_poll_in_busy(dev);
645 	if (ret < 0)
646 		return ret;
647 
648 	/* Should check status before starting FLASH access sequence */
649 
650 	/* Wait for status information */
651 	ret = c2port_poll_out_ready(dev);
652 	if (ret < 0)
653 		return ret;
654 
655 	/* Read flash programming interface status */
656 	ret = c2port_read_dr(dev, &status);
657 	if (ret < 0)
658 		return ret;
659 	if (status != C2PORT_COMMAND_OK)
660 		return -EBUSY;
661 
662 	/* Send address high byte */
663 	c2port_write_dr(dev, offset >> 8);
664 	ret = c2port_poll_in_busy(dev);
665 	if (ret < 0)
666 		return ret;
667 
668 	/* Send address low byte */
669 	c2port_write_dr(dev, offset & 0x00ff);
670 	ret = c2port_poll_in_busy(dev);
671 	if (ret < 0)
672 		return ret;
673 
674 	/* Send address block size */
675 	c2port_write_dr(dev, nread);
676 	ret = c2port_poll_in_busy(dev);
677 	if (ret < 0)
678 		return ret;
679 
680 	/* Should check status before reading FLASH block */
681 
682 	/* Wait for status information */
683 	ret = c2port_poll_out_ready(dev);
684 	if (ret < 0)
685 		return ret;
686 
687 	/* Read flash programming interface status */
688 	ret = c2port_read_dr(dev, &status);
689 	if (ret < 0)
690 		return ret;
691 	if (status != C2PORT_COMMAND_OK)
692 		return -EBUSY;
693 
694 	/* Read flash block */
695 	for (i = 0; i < nread; i++) {
696 		ret = c2port_poll_out_ready(dev);
697 		if (ret < 0)
698 			return ret;
699 
700 		ret = c2port_read_dr(dev, buffer+i);
701 		if (ret < 0)
702 			return ret;
703 	}
704 
705 	return nread;
706 }
707 
708 static ssize_t c2port_read_flash_data(struct kobject *kobj,
709 				struct bin_attribute *attr,
710 				char *buffer, loff_t offset, size_t count)
711 {
712 	struct c2port_device *c2dev =
713 			dev_get_drvdata(container_of(kobj,
714 						struct device, kobj));
715 	ssize_t ret;
716 
717 	/* Check the device and flash access status */
718 	if (!c2dev->access || !c2dev->flash_access)
719 		return -EBUSY;
720 
721 	mutex_lock(&c2dev->mutex);
722 	ret = __c2port_read_flash_data(c2dev, buffer, offset, count);
723 	mutex_unlock(&c2dev->mutex);
724 
725 	if (ret < 0)
726 		dev_err(c2dev->dev, "cannot read %s flash\n", c2dev->name);
727 
728 	return ret;
729 }
730 
731 static ssize_t __c2port_write_flash_data(struct c2port_device *dev,
732 				char *buffer, loff_t offset, size_t count)
733 {
734 	struct c2port_ops *ops = dev->ops;
735 	u8 status, nwrite = 128;
736 	int i, ret;
737 
738 	if (nwrite > count)
739 		nwrite = count;
740 	if (ops->block_size * ops->blocks_num - offset < nwrite)
741 		nwrite = ops->block_size * ops->blocks_num - offset;
742 
743 	/* Check for flash end */
744 	if (offset >= ops->block_size * ops->blocks_num)
745 		return -EINVAL;
746 
747 	/* Target the C2 flash programming data register for C2 data register
748 	 * access */
749 	c2port_write_ar(dev, C2PORT_FPDAT);
750 
751 	/* Send flash block write command */
752 	c2port_write_dr(dev, C2PORT_BLOCK_WRITE);
753 
754 	/* Wait for input acknowledge */
755 	ret = c2port_poll_in_busy(dev);
756 	if (ret < 0)
757 		return ret;
758 
759 	/* Should check status before starting FLASH access sequence */
760 
761 	/* Wait for status information */
762 	ret = c2port_poll_out_ready(dev);
763 	if (ret < 0)
764 		return ret;
765 
766 	/* Read flash programming interface status */
767 	ret = c2port_read_dr(dev, &status);
768 	if (ret < 0)
769 		return ret;
770 	if (status != C2PORT_COMMAND_OK)
771 		return -EBUSY;
772 
773 	/* Send address high byte */
774 	c2port_write_dr(dev, offset >> 8);
775 	ret = c2port_poll_in_busy(dev);
776 	if (ret < 0)
777 		return ret;
778 
779 	/* Send address low byte */
780 	c2port_write_dr(dev, offset & 0x00ff);
781 	ret = c2port_poll_in_busy(dev);
782 	if (ret < 0)
783 		return ret;
784 
785 	/* Send address block size */
786 	c2port_write_dr(dev, nwrite);
787 	ret = c2port_poll_in_busy(dev);
788 	if (ret < 0)
789 		return ret;
790 
791 	/* Should check status before writing FLASH block */
792 
793 	/* Wait for status information */
794 	ret = c2port_poll_out_ready(dev);
795 	if (ret < 0)
796 		return ret;
797 
798 	/* Read flash programming interface status */
799 	ret = c2port_read_dr(dev, &status);
800 	if (ret < 0)
801 		return ret;
802 	if (status != C2PORT_COMMAND_OK)
803 		return -EBUSY;
804 
805 	/* Write flash block */
806 	for (i = 0; i < nwrite; i++) {
807 		ret = c2port_write_dr(dev, *(buffer+i));
808 		if (ret < 0)
809 			return ret;
810 
811 		ret = c2port_poll_in_busy(dev);
812 		if (ret < 0)
813 			return ret;
814 
815 	}
816 
817 	/* Wait for last flash write to complete */
818 	ret = c2port_poll_out_ready(dev);
819 	if (ret < 0)
820 		return ret;
821 
822 	return nwrite;
823 }
824 
825 static ssize_t c2port_write_flash_data(struct kobject *kobj,
826 				struct bin_attribute *attr,
827 				char *buffer, loff_t offset, size_t count)
828 {
829 	struct c2port_device *c2dev =
830 			dev_get_drvdata(container_of(kobj,
831 						struct device, kobj));
832 	int ret;
833 
834 	/* Check the device access status */
835 	if (!c2dev->access || !c2dev->flash_access)
836 		return -EBUSY;
837 
838 	mutex_lock(&c2dev->mutex);
839 	ret = __c2port_write_flash_data(c2dev, buffer, offset, count);
840 	mutex_unlock(&c2dev->mutex);
841 
842 	if (ret < 0)
843 		dev_err(c2dev->dev, "cannot write %s flash\n", c2dev->name);
844 
845 	return ret;
846 }
847 
848 /*
849  * Class attributes
850  */
851 
852 static struct device_attribute c2port_attrs[] = {
853 	__ATTR(name, 0444, c2port_show_name, NULL),
854 	__ATTR(flash_blocks_num, 0444, c2port_show_flash_blocks_num, NULL),
855 	__ATTR(flash_block_size, 0444, c2port_show_flash_block_size, NULL),
856 	__ATTR(flash_size, 0444, c2port_show_flash_size, NULL),
857 	__ATTR(access, 0644, c2port_show_access, c2port_store_access),
858 	__ATTR(reset, 0200, NULL, c2port_store_reset),
859 	__ATTR(dev_id, 0444, c2port_show_dev_id, NULL),
860 	__ATTR(rev_id, 0444, c2port_show_rev_id, NULL),
861 
862 	__ATTR(flash_access, 0644, c2port_show_flash_access,
863 					c2port_store_flash_access),
864 	__ATTR(flash_erase, 0200, NULL, c2port_store_flash_erase),
865 	__ATTR_NULL,
866 };
867 
868 static struct bin_attribute c2port_bin_attrs = {
869 	.attr	= {
870 		.name	= "flash_data",
871 		.mode	= 0644
872 	},
873 	.read	= c2port_read_flash_data,
874 	.write	= c2port_write_flash_data,
875 	/* .size is computed at run-time */
876 };
877 
878 /*
879  * Exported functions
880  */
881 
882 struct c2port_device *c2port_device_register(char *name,
883 					struct c2port_ops *ops, void *devdata)
884 {
885 	struct c2port_device *c2dev;
886 	int id, ret;
887 
888 	if (unlikely(!ops) || unlikely(!ops->access) || \
889 		unlikely(!ops->c2d_dir) || unlikely(!ops->c2ck_set) || \
890 		unlikely(!ops->c2d_get) || unlikely(!ops->c2d_set))
891 		return ERR_PTR(-EINVAL);
892 
893 	c2dev = kmalloc(sizeof(struct c2port_device), GFP_KERNEL);
894 	if (unlikely(!c2dev))
895 		return ERR_PTR(-ENOMEM);
896 
897 	ret = idr_pre_get(&c2port_idr, GFP_KERNEL);
898 	if (!ret) {
899 		ret = -ENOMEM;
900 		goto error_idr_get_new;
901 	}
902 
903 	spin_lock_irq(&c2port_idr_lock);
904 	ret = idr_get_new(&c2port_idr, c2dev, &id);
905 	spin_unlock_irq(&c2port_idr_lock);
906 
907 	if (ret < 0)
908 		goto error_idr_get_new;
909 	c2dev->id = id;
910 
911 	c2dev->dev = device_create(c2port_class, NULL, 0, c2dev,
912 					"c2port%d", id);
913 	if (unlikely(!c2dev->dev)) {
914 		ret = -ENOMEM;
915 		goto error_device_create;
916 	}
917 	dev_set_drvdata(c2dev->dev, c2dev);
918 
919 	strncpy(c2dev->name, name, C2PORT_NAME_LEN);
920 	c2dev->ops = ops;
921 	mutex_init(&c2dev->mutex);
922 
923 	/* Create binary file */
924 	c2port_bin_attrs.size = ops->blocks_num * ops->block_size;
925 	ret = device_create_bin_file(c2dev->dev, &c2port_bin_attrs);
926 	if (unlikely(ret))
927 		goto error_device_create_bin_file;
928 
929 	/* By default C2 port access is off */
930 	c2dev->access = c2dev->flash_access = 0;
931 	ops->access(c2dev, 0);
932 
933 	dev_info(c2dev->dev, "C2 port %s added\n", name);
934 	dev_info(c2dev->dev, "%s flash has %d blocks x %d bytes "
935 				"(%d bytes total)\n",
936 				name, ops->blocks_num, ops->block_size,
937 				ops->blocks_num * ops->block_size);
938 
939 	return c2dev;
940 
941 error_device_create_bin_file:
942 	device_destroy(c2port_class, 0);
943 
944 error_device_create:
945 	spin_lock_irq(&c2port_idr_lock);
946 	idr_remove(&c2port_idr, id);
947 	spin_unlock_irq(&c2port_idr_lock);
948 
949 error_idr_get_new:
950 	kfree(c2dev);
951 
952 	return ERR_PTR(ret);
953 }
954 EXPORT_SYMBOL(c2port_device_register);
955 
956 void c2port_device_unregister(struct c2port_device *c2dev)
957 {
958 	if (!c2dev)
959 		return;
960 
961 	dev_info(c2dev->dev, "C2 port %s removed\n", c2dev->name);
962 
963 	device_remove_bin_file(c2dev->dev, &c2port_bin_attrs);
964 	spin_lock_irq(&c2port_idr_lock);
965 	idr_remove(&c2port_idr, c2dev->id);
966 	spin_unlock_irq(&c2port_idr_lock);
967 
968 	device_destroy(c2port_class, c2dev->id);
969 
970 	kfree(c2dev);
971 }
972 EXPORT_SYMBOL(c2port_device_unregister);
973 
974 /*
975  * Module stuff
976  */
977 
978 static int __init c2port_init(void)
979 {
980 	printk(KERN_INFO "Silicon Labs C2 port support v. " DRIVER_VERSION
981 		" - (C) 2007 Rodolfo Giometti\n");
982 
983 	c2port_class = class_create(THIS_MODULE, "c2port");
984 	if (!c2port_class) {
985 		printk(KERN_ERR "c2port: failed to allocate class\n");
986 		return -ENOMEM;
987 	}
988 	c2port_class->dev_attrs = c2port_attrs;
989 
990 	return 0;
991 }
992 
993 static void __exit c2port_exit(void)
994 {
995 	class_destroy(c2port_class);
996 }
997 
998 module_init(c2port_init);
999 module_exit(c2port_exit);
1000 
1001 MODULE_AUTHOR("Rodolfo Giometti <giometti@linux.it>");
1002 MODULE_DESCRIPTION("Silicon Labs C2 port support v. " DRIVER_VERSION);
1003 MODULE_LICENSE("GPL");
1004