Commit ccd742da authored by Miguel Gómez Sexto's avatar Miguel Gómez Sexto

Removed init() and exit() fuctions of the library. Changed open() and close()

to work with lun ids.
Added a ZIO attribute to the device to hold its lun, so the library can read
it.
Signed-off-by: Miguel Gómez Sexto's avatarMiguel Gomez <magomez@igalia.com>
parent 2e8afbf1
......@@ -43,7 +43,7 @@ static struct zio_attribute tdc_zattr_dev[] = {
TDC_ATTR_DEV_ACTIVATE_ACQUISITION, 0),
ZATTR_EXT_REG("get_wr_pointer", _RW_,
TDC_ATTR_DEV_GET_POINTER, 0),
ZATTR_EXT_REG("lun", S_IRUGO, TDC_ATTR_DEV_LUN, 1),
};
static struct zio_cset tdc_cset[] = {
......@@ -190,6 +190,9 @@ static int tdc_zio_info_get(struct device *dev,
case TDC_ATTR_DEV_GET_POINTER:
*usr_val = tdc_get_circular_buffer_wr_pointer(tdc);
break;
case TDC_ATTR_DEV_LUN:
/* FIXME: add code to return real lun */
break;
default:
return -EINVAL;
......
......@@ -47,6 +47,7 @@ enum tdc_zattr_dev_idx {
TDC_ATTR_DEV_DAC_WORD,
TDC_ATTR_DEV_ACTIVATE_ACQUISITION,
TDC_ATTR_DEV_GET_POINTER,
TDC_ATTR_DEV_LUN,
TDC_ATTR_DEV__LAST,
};
......
......@@ -14,11 +14,29 @@
#define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0]))
static int tdc_nboards;
static struct tdc_board *tdc_boards;
static inline int __tdc_sysfs_get_lun(char *sysbase, uint32_t *resp)
{
char path[128];
FILE *f;
sprintf(path, "%s/%s", sysbase, "lun");
f = fopen(path, "r");
if (!f)
return -1;
errno = 0;
if (fscanf(f, "%i", resp) != 1) {
fclose(f);
if (!errno)
errno = EINVAL;
return -1;
}
fclose(f);
return 0;
}
static inline int __tdc_sysfs_get(struct tdc_board *b, char *name,
uint32_t *resp)
uint32_t *resp)
{
char path[128];
FILE *f;
......@@ -40,7 +58,7 @@ static inline int __tdc_sysfs_get(struct tdc_board *b, char *name,
}
static inline int __tdc_sysfs_set(struct tdc_board *b, char *name,
uint32_t value)
uint32_t value)
{
char path[128];
char s[16];
......@@ -61,10 +79,13 @@ static inline int __tdc_sysfs_set(struct tdc_board *b, char *name,
return -1;
}
int tdc_init(void)
struct tdc_board *tdc_open(int lun)
{
glob_t glob_dev, glob_sys;
struct tdc_board *b;
struct tdc_board *b = NULL;
int tdc_nboards;
int ret;
uint32_t dev_lun;
int i, j;
/* Look for boards in /dev: old and new pathnames: only one matches */
......@@ -75,20 +96,30 @@ int tdc_init(void)
glob("/sys/bus/zio/devices/tdc-*",0 , NULL, &glob_sys);
assert(glob_dev.gl_pathc == glob_sys.gl_pathc);
/* Allocate as needed */
/* Check that there are boards found */
tdc_nboards = glob_dev.gl_pathc;
if (!tdc_nboards) {
tdc_boards = NULL;
return 0;
}
tdc_boards = calloc(glob_dev.gl_pathc, sizeof(tdc_boards[0]));
if (!tdc_boards) {
globfree(&glob_dev);
globfree(&glob_sys);
return -1;
fprintf (stderr, "No boards found!\n");
errno = ENODEV;
return NULL;
}
for (i = 0, b = tdc_boards; i < tdc_nboards; i++, b++) {
for (i = 0; i < tdc_nboards; i++) {
ret = __tdc_sysfs_get_lun(glob_sys.gl_pathv[i], &dev_lun);
/* Unable to get lun */
if (ret < 0) {
fprintf(stderr, "Unable to get lun for device %s\n",
glob_sys.gl_pathv[i]);
continue;
}
/* lun doesn't match */
if (dev_lun != lun)
continue;
/* lun found */
b = malloc(sizeof(struct tdc_board));
b->lun = lun;
b->sysbase = strdup(glob_sys.gl_pathv[i]);
b->devbase = strdup(glob_dev.gl_pathv[i]);
/* trim the "-0-0-ctrl" at the end */
......@@ -100,79 +131,15 @@ int tdc_init(void)
b->data[j] = -1;
b->enabled[j] = 0;
}
printf("Found device %s\n", b->sysbase);
break;
}
globfree(&glob_dev);
globfree(&glob_sys);
return tdc_nboards;
}
void tdc_exit(void)
{
struct tdc_board *b;
int i, j, err;
for (i = 0, err = 0, b = tdc_boards; i < tdc_nboards; i++, b++) {
for (j = 0; j < ARRAY_SIZE(b->ctrl); j++) {
if (b->ctrl[j] >= 0) {
close(b->ctrl[j]);
b->ctrl[j] = -1;
err++;
}
if (b->data[j] >= 0) {
close(b->data[j]);
b->data[j] = -1;
err++;
}
b->enabled[j] = 0;
}
if (err)
fprintf(stderr, "%s: device %s was still open\n",
__func__, b->devbase);
free(b->sysbase);
free(b->devbase);
}
if(tdc_nboards)
free(tdc_boards);
}
struct tdc_board *tdc_open(int offset, int dev_id)
{
struct tdc_board *b = NULL;
int i;
/* If we are given an offset, select the dev there */
/* If we are given an id, loop until we find it in the list */
/* If we are given an offset and an id, the id in pos offset must match */
if (offset >= tdc_nboards) {
if (!b)
errno = ENODEV;
return NULL;
}
if (offset >= 0) {
b = tdc_boards + offset;
if (dev_id >= 0 && dev_id != b->dev_id) {
errno = EINVAL;
return NULL;
}
goto found;
}
if (dev_id < 0) {
errno = EINVAL;
return NULL;
}
for (i = 0, b = tdc_boards; i < tdc_nboards; i++, b++)
if (b->dev_id == dev_id)
goto found;
errno = ENODEV;
return NULL;
found:
printf("Opened device %s\n", b->sysbase);
return b;
}
......@@ -181,13 +148,23 @@ int tdc_close(struct tdc_board *b)
int j;
for (j = 0; j < ARRAY_SIZE(b->ctrl); j++) {
if (b->ctrl[j] >= 0)
if (b->ctrl[j] >= 0) {
close(b->ctrl[j]);
fprintf(stderr, "Device %s was still open\n",
b->devbase);
}
b->ctrl[j] = -1;
if (b->data[j] >= 0)
if (b->data[j] >= 0) {
close(b->data[j]);
fprintf(stderr, "Device %s was still open\n",
b->devbase);
}
b->data[j] = -1;
}
free(b->sysbase);
free(b->devbase);
free(b);
return 0;
}
......
......@@ -5,6 +5,7 @@
struct tdc_board {
int dev_id;
int lun;
char *devbase;
char *sysbase;
int ctrl[5]; /* The 5 control channels */
......@@ -26,10 +27,7 @@ enum {
CHAN4 = 1 << 4
};
extern int tdc_init(void);
extern void tdc_exit(void);
extern struct tdc_board *tdc_open(int offset, int dev_id);
extern struct tdc_board *tdc_open(int lun);
extern int tdc_close(struct tdc_board *b);
extern int tdc_start_acquisition(struct tdc_board *b);
......
......@@ -7,25 +7,9 @@
int main(int argc, char **argv)
{
struct tdc_board *b;
int i;
uint32_t set, get;
i = tdc_init();
if (i < 0) {
fprintf(stderr, "%s: tdc_init(): %s\n", argv[0],
strerror(errno));
exit(1);
}
if (i == 0) {
fprintf(stderr, "%s: no boards found\n", argv[0]);
exit(1);
}
if (i != 1) {
fprintf(stderr, "%s: found %i boards\n",
argv[0], i);
}
b = tdc_open(0, -1);
b = tdc_open(1);
/* set/get UTC time */
set = 123;
......@@ -85,6 +69,5 @@ int main(int argc, char **argv)
tdc_close(b);
tdc_exit();
return 0;
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment