ref: ffb48be969338833a69e576e7d62353bbd831226
parent: a1a4ae4a53640eea33c76b41ecbbd7a091e019f8
author: Sigrid Solveig Haflínudóttir <sigrid@ftrv.se>
date: Thu Sep 8 16:20:11 EDT 2022
reform/pm: serve lpc readouts over a queue to avoid lockups on other requests
--- a/sys/src/cmd/reform/pm.c
+++ b/sys/src/cmd/reform/pm.c
@@ -68,7 +68,7 @@
STAT_RR = 1<<3,
};
-static char lpcfw[9*3+1];
+static Reqqueue *lpcreq;
static u32int *pwm2, *tmu, *spi2;
static char *uid = "pm";
@@ -225,22 +225,12 @@
}
static void
-lpcinit(void)
+readbattery(Req *r)
{
- char s[3][8];
-
- lpccall('f', 0, s[0]);
- lpccall('f', 1, s[1]);
- lpccall('f', 2, s[2]);
- snprint(lpcfw, sizeof(lpcfw), "%.*s %.*s %.*s", 8, s[0], 8, s[1], 8, s[2]);
-}
-
-static char *
-readbattery(char *s, char *e)
-{
int hh, mm, ss, full, remain, warn, safe;
u8int st[8], ch[8];
s16int current;
+ char msg[256];
char *state;
lpccall('c', 0, ch);
@@ -272,11 +262,12 @@
}
break;
case Smissing:
- werrstr("battery is missing");
- return nil;
+ respond(r, "battery is missing");
+ return;
+
}
- return seprint(s, e, "%d mA %d %d %d %d ? mV %d ? %02d:%02d:%02d %s\n",
+ snprint(msg, sizeof(msg), "%d mA %d %d %d %d ? mV %d ? %02d:%02d:%02d %s\n",
st[4],
remain, full, full, warn,
st[0]|st[1]<<8,
@@ -283,35 +274,47 @@
hh, mm, ss,
state
);
+
+ readstr(r, msg);
+ respond(r, nil);
}
-static char *
-readcells(char *s, char *e)
+static void
+readpmctl(Req *r)
{
- u8int v[16];
+ char msg[256], *s, *e;
+ static char lpcfw[9*3+1];
+ u8int v[16], q[8];
int i;
+ if(lpcfw[0] == 0){
+ lpccall('f', 0, msg+0);
+ lpccall('f', 1, msg+8);
+ lpccall('f', 2, msg+16);
+ snprint(lpcfw, sizeof(lpcfw), "%.*s %.*s %.*s", 8, msg+0, 8, msg+8, 8, msg+16);
+ }
lpccall('v', 0, v+0);
lpccall('v', 1, v+8);
+ lpccall('q', 0, q);
+
+ s = msg;
+ e = s+sizeof(msg);
+ s = seprint(s, e, "version %s\n", lpcfw);
s = seprint(s, e, "cells(mV)");
for(i = 0; i < 16; i += 2)
s = seprint(s, e, " %d", v[i] | v[i+1]<<8);
- return seprint(s, e, "\n");
-}
+ s = seprint(s, e, "\n");
+ s = seprint(s, e, "current(mA) %d\n", (s16int)(q[2] | q[3]<<8));
+ USED(s);
-static char *
-readcurrent(char *s, char *e)
-{
- u8int q[8];
-
- lpccall('q', 0, q);
- return seprint(s, e, "current(mA) %d\n", (s16int)(q[2] | q[3]<<8));
+ readstr(r, msg);
+ respond(r, nil);
}
static void
fsread(Req *r)
{
- char msg[256], *s, *e;
+ char msg[256];
void *aux;
int c[3];
@@ -318,8 +321,6 @@
msg[0] = 0;
if(r->ifcall.offset == 0){
aux = r->fid->file->aux;
- s = msg;
- e = s+sizeof(msg);
if(aux == (void*)Light){
snprint(msg, sizeof(msg), "lcd %d\n", getlight());
}else if(aux == (void*)Temp){
@@ -330,15 +331,11 @@
/* only the first one is CPU temperature */
snprint(msg, sizeof(msg), "%d.0\n", c[0]);
}else if(aux == (void*)Battery){
- if(readbattery(s, e) == nil){
- responderror(r);
- return;
- }
+ reqqueuepush(lpcreq, r, readbattery);
+ return;
}else if(aux == (void*)Pmctl){
- s = seprint(s, e, "version %s\n", lpcfw);
- s = readcells(s, e);
- s = readcurrent(s, e);
- USED(s);
+ reqqueuepush(lpcreq, r, readpmctl);
+ return;
}
}
@@ -382,9 +379,23 @@
respond(r, nil);
}
+static void
+fsflush(Req *r)
+{
+ void *aux;
+ Req *o;
+
+ o = r->oldreq;
+ aux = o->fid->file->aux;
+ if(o->ifcall.type == Tread && (aux == (void*)Battery || aux == (void*)Pmctl))
+ reqqueueflush(lpcreq, o);
+ respond(r, nil);
+}
+
static Srv fs = {
.read = fsread,
.write = fswrite,
+ .flush = fsflush,
};
static void
@@ -395,7 +406,7 @@
}
void
-main(int argc, char **argv)
+threadmain(int argc, char **argv)
{
char *mtpt, *srv;
@@ -422,13 +433,13 @@
if((spi2 = segattach(0, "ecspi2", 0, 0x20)) == (void*)-1)
sysfatal("no spi2");
tmuinit();
- lpcinit();
+ lpcreq = reqqueuecreate();
fs.tree = alloctree(uid, uid, DMDIR|0555, nil);
createfile(fs.tree->root, "battery", uid, 0444,(void*)Battery);
createfile(fs.tree->root, "cputemp", uid, 0444, (void*)Temp);
createfile(fs.tree->root, "light", uid, 0666, (void*)Light);
createfile(fs.tree->root, "pmctl", uid, 0666, (void*)Pmctl);
- postmountsrv(&fs, srv, mtpt, MAFTER);
+ threadpostmountsrv(&fs, srv, mtpt, MAFTER);
- exits(nil);
+ threadexits(nil);
}