Add SIOCTL_SEL control type

This commit is contained in:
Alexandre Ratchov 2020-06-16 07:16:26 +02:00
parent 9bfc9cf713
commit 14b0682012
5 changed files with 52 additions and 14 deletions

View File

@ -127,6 +127,7 @@ struct sioctl_desc {
#define SIOCTL_SW 3 /* on/off switch (0 or 1) */
#define SIOCTL_VEC 4 /* number, element of vector */
#define SIOCTL_LIST 5 /* switch, element of a list */
#define SIOCTL_SEL 6 /* element of a selector */
unsigned int type; /* one of above */
char func[SIOCTL_NAMEMAX]; /* function name, ex. "level" */
char group[SIOCTL_NAMEMAX]; /* group this control belongs to */
@ -167,6 +168,10 @@ from the line input to the speaker.
An element of an array of on/off switches.
For instance the line-in position of the
speaker source selector.
.It SIOCTL_SEL
Same as
.Va SIOCTL_LIST
but exactly one element is selected at a time.
.El
.Pp
The
@ -182,9 +187,10 @@ attributes indicate the names of the controlled nodes, typically
channels of audio streams.
.Va node1
is meaningful for
.Va SIOCTL_VEC
.Va SIOCTL_VEC ,
.Va SIOCTL_LIST ,
and
.Va SIOCTL_LIST
.Va SIOCTL_SEL
only.
.Pp
Names in the

View File

@ -108,6 +108,7 @@ struct sioctl_desc {
#define SIOCTL_SW 3 /* on/off switch (0 or 1) */
#define SIOCTL_VEC 4 /* number, element of vector */
#define SIOCTL_LIST 5 /* switch, element of a list */
#define SIOCTL_SEL 6 /* element of a selector */
unsigned int type; /* one of above */
char func[SIOCTL_NAMEMAX]; /* function name, ex. "level" */
char group[SIOCTL_NAMEMAX]; /* group this control belongs to */

View File

@ -107,7 +107,8 @@ cmpdesc(struct sioctl_desc *d1, struct sioctl_desc *d2)
if (res != 0)
return res;
res = d1->node0.unit - d2->node0.unit;
if (d1->type == SIOCTL_VEC ||
if (d1->type == SIOCTL_SEL ||
d1->type == SIOCTL_VEC ||
d1->type == SIOCTL_LIST) {
if (res != 0)
return res;
@ -297,6 +298,7 @@ ismono(struct info *g)
return 0;
}
break;
case SIOCTL_SEL:
case SIOCTL_VEC:
case SIOCTL_LIST:
for (p2 = g; p2 != NULL; p2 = nextpar(p2)) {
@ -345,6 +347,7 @@ print_desc(struct info *p, int mono)
case SIOCTL_SW:
printf("*");
break;
case SIOCTL_SEL:
case SIOCTL_VEC:
case SIOCTL_LIST:
more = 0;
@ -358,7 +361,8 @@ print_desc(struct info *p, int mono)
if (more)
printf(",");
print_node(&e->desc.node1, mono);
printf(":*");
if (p->desc.type != SIOCTL_SEL)
printf(":*");
more = 1;
}
}
@ -394,6 +398,7 @@ print_ent(struct info *e, char *comment)
case SIOCTL_NONE:
printf("<removed>\n");
break;
case SIOCTL_SEL:
case SIOCTL_VEC:
case SIOCTL_LIST:
print_node(&e->desc.node1, 0);
@ -422,6 +427,7 @@ print_val(struct info *p, int mono)
case SIOCTL_SW:
print_num(p);
break;
case SIOCTL_SEL:
case SIOCTL_VEC:
case SIOCTL_LIST:
more = 0;
@ -621,6 +627,9 @@ dump(void)
case SIOCTL_SW:
printf("0..%d (%u)", i->desc.maxval, i->curval);
break;
case SIOCTL_SEL:
print_node(&i->desc.node1, 0);
break;
case SIOCTL_VEC:
case SIOCTL_LIST:
print_node(&i->desc.node1, 0);
@ -700,6 +709,7 @@ cmd(char *line)
npar++;
}
break;
case SIOCTL_SEL:
case SIOCTL_VEC:
case SIOCTL_LIST:
for (i = g; i != NULL; i = nextpar(i)) {
@ -889,17 +899,36 @@ ondesc(void *arg, struct sioctl_desc *d, int curval)
void
onctl(void *arg, unsigned addr, unsigned val)
{
struct info *i;
struct info *i, *j;
for (i = infolist; i != NULL; i = i->next) {
if (i->ctladdr != addr)
continue;
if (i->curval != val) {
i->curval = val;
if (m_flag)
print_ent(i, "changed");
}
i = infolist;
for (;;) {
if (i == NULL)
return;
if (i->ctladdr == addr)
break;
i = i->next;
}
if (i->curval == val) {
print_ent(i, "eq");
return;
}
if (i->desc.type == SIOCTL_SEL) {
for (j = infolist; j != NULL; j = j->next) {
if (strcmp(i->desc.group, j->desc.group) != 0 ||
strcmp(i->desc.node0.name, j->desc.node0.name) != 0 ||
strcmp(i->desc.func, j->desc.func) != 0 ||
i->desc.node0.unit != j->desc.node0.unit)
continue;
j->curval = (i->ctladdr == j->ctladdr);
}
} else
i->curval = val;
if (m_flag)
print_ent(i, "changed");
}
int

View File

@ -2297,6 +2297,7 @@ ctl_log(struct ctl *c)
break;
case CTL_VEC:
case CTL_LIST:
case CTL_SEL:
ctl_node_log(&c->node1);
log_puts(":");
log_putu(c->curval);
@ -2321,7 +2322,7 @@ dev_addctl(struct dev *d, char *gstr, int type, int addr,
strlcpy(c->group, gstr, CTL_NAMEMAX);
strlcpy(c->node0.name, str0, CTL_NAMEMAX);
c->node0.unit = unit0;
if (c->type == CTL_VEC || c->type == CTL_LIST) {
if (c->type == CTL_VEC || c->type == CTL_LIST || c->type == CTL_SEL) {
strlcpy(c->node1.name, str1, CTL_NAMEMAX);
c->node1.unit = unit1;
} else

View File

@ -126,6 +126,7 @@ struct ctl {
#define CTL_SW 3 /* on/off switch, only bit 7 counts */
#define CTL_VEC 4 /* number, element of vector */
#define CTL_LIST 5 /* switch, element of a list */
#define CTL_SEL 6 /* element of a selector */
unsigned int type; /* one of above */
unsigned int addr; /* control address */
#define CTL_NAMEMAX 16 /* max name lenght */