* email:pisa@cmp.felk.cvut.cz
* This software is released under the GPL-License.
* Version lincan-0.3 17 Jun 2004
- */
+ */
#include "../include/can.h"
#include "../include/can_sysdep.h"
static int can_proc_readlink(struct proc_dir_entry *ent, char *page);
#endif
+#if LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,25)
+#define CAN_PROC_ROOT (&proc_root)
+#else /* >= 2.6.26 */
+#define CAN_PROC_ROOT (NULL)
+#endif /* >= 2.6.26 */
+
static int cc=0; /* static counter for each CAN chip */
static struct canproc_t can_proc_base;
struct proc_dir_entry *new_entry = NULL;
char *namestore;
int namelen;
-
+
if(!name || !parent)
return NULL;
namelen=strlen(name);
if(!namelen)
return NULL;
- new_entry = (struct proc_dir_entry *)
+ new_entry = (struct proc_dir_entry *)
can_checked_malloc(sizeof(struct proc_dir_entry)+namelen+1);
if (new_entry == NULL)
static int can_proc_readlink(struct proc_dir_entry *ent, char *page)
{
char *link_dest = (char*)ent->data;
-
+
strcpy(page, link_dest);
return strlen(link_dest);
}
struct proc_dir_entry *parent, const char *dest)
{
struct proc_dir_entry *entry;
-
-
+
+
entry = can_create_proc_entry(name, S_IFLNK | S_IRUGO | S_IWUGO | S_IXUGO, parent);
if (entry == NULL)
return NULL;
{
int board;
struct candevice_t *candev;
- base->can_proc_entry = can_create_proc_entry("can", S_IFDIR | S_IRUGO |
- S_IXUGO, &proc_root);
+ base->can_proc_entry = can_create_proc_entry("can", S_IFDIR | S_IRUGO |
+ S_IXUGO, CAN_PROC_ROOT);
if (base->can_proc_entry == NULL)
return -ENODEV;
for (board=0; board<hardware_p->nr_boards; board++) {
candev=hardware_p->candevice[board];
if(candev) add_channel_to_procdir(candev);
- }
+ }
return 0;
}
if (remove_channel_from_procdir())
return -ENODEV;
/* name: "can" */
- if (can_remove_proc_entry(base->can_proc_entry, &proc_root))
+ if (can_remove_proc_entry(base->can_proc_entry, CAN_PROC_ROOT))
return -ENODEV;
return 0;
}
+static int can_chip_procinfo(char *buf, char **start, off_t offset,
+ int count, int *eof, void *data)
+{
+ struct canchip_t *chip=data;
+ int len=0;
+
+ /* Generic chip info */
+ len += sprintf(buf+len,"type : %s\n",chip->chip_type);
+ len += sprintf(buf+len,"index : %d\n",chip->chip_idx);
+ len += sprintf(buf+len,"irq : %d\n",chip->chip_irq);
+ len += sprintf(buf+len,"addr : %lu\n",
+ can_ioptr2ulong(chip->chip_base_addr));
+ len += sprintf(buf+len,"config : %s\n",
+ (chip->flags & CHIP_CONFIGURED) ? "yes":"no");
+ len += sprintf(buf+len,"clock : %ld Hz\n",chip->clock);
+ len += sprintf(buf+len,"baud : %ld\n",chip->baudrate);
+ len += sprintf(buf+len,"num obj : %d\n",chip->max_objects);
+
+
+#if 0
+ /* Chip specific info if available */
+ if(chip->chipspecops->get_info)
+ len += (chip->chipspecops->get_info)(chip,buf+len);
+#endif
+
+ *eof = 1;
+ return len;
+}
+
+
int add_channel_to_procdir(struct candevice_t *candev)
{
int i=0;
return -ENOMEM;
sprintf(base->channel[cc]->ch_name, "channel%d",cc);
-
+
base->channel[cc]->ch_entry = can_create_proc_entry(
base->channel[cc]->ch_name,
S_IFDIR | S_IRUGO |S_IXUGO,
add_object_to_procdir(cc);
+ create_proc_read_entry("chip_info", /* proc entry name */
+ 0, /* protection mask, 0->default */
+ base->channel[cc]->ch_entry, /* parent dir, NULL->/proc */
+ can_chip_procinfo,
+ candev->chip[i]);
+
cc++;
- }
+ }
return 0;
}
int remove_channel_from_procdir(void)
{
-
+
while (cc != 0) {
cc--;
-
+
if(!base->channel[cc]) continue;
-
+
+ remove_proc_entry("chip_info", base->channel[cc]->ch_entry);
+
if (remove_object_from_procdir(cc))
- return -ENODEV;
-
+ return -ENODEV;
+
/* name: base->channel[cc]->ch_name */
if (can_remove_proc_entry(base->channel[cc]->ch_entry,
base->can_proc_entry))
return -ENODEV;
-
+
can_checked_free(base->channel[cc]);
base->channel[cc] = NULL;
}
sprintf(base->channel[chip_nr]->object[i]->obj_name,"object%d",i);
sprintf(base->channel[chip_nr]->object[i]->lnk_name,"dev");
-
+
base->channel[chip_nr]->object[i]->obj_entry = can_create_proc_entry(
base->channel[chip_nr]->object[i]->obj_name,
S_IFDIR | S_IRUGO | S_IXUGO,
}
return 0;
-}
+}
int remove_object_from_procdir(int chip_nr)
{
for (i=0; i<obj; i++) {
if(!base->channel[chip_nr]->object[i]) continue;
-
+
/* name: base->channel[chip_nr]->object[i]->lnk_name */
if (can_remove_proc_entry( base->channel[chip_nr]->object[i]->lnk,
- base->channel[chip_nr]->object[i]->obj_entry))
+ base->channel[chip_nr]->object[i]->obj_entry))
return -ENODEV;
/* name: base->channel[chip_nr]->object[i]->obj_name */
if (can_remove_proc_entry(