cleanup: simplify frontend request ownership
This commit is contained in:
3
dat.h
3
dat.h
@@ -154,12 +154,11 @@ struct Keyres
|
|||||||
|
|
||||||
struct Keyreq
|
struct Keyreq
|
||||||
{
|
{
|
||||||
uvlong owner;
|
void *owner; /* stable until the context's release is acknowledged */
|
||||||
int op;
|
int op;
|
||||||
u32int ks;
|
u32int ks;
|
||||||
u32int mod;
|
u32int mod;
|
||||||
Caret caret;
|
Caret caret;
|
||||||
int want; /* nonzero: include preedit in reply */
|
|
||||||
Channel *reply;
|
Channel *reply;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
2
fn.h
2
fn.h
@@ -36,8 +36,6 @@ Emit transko(Im*, Rune);
|
|||||||
Emit transvi(Im*, Rune);
|
Emit transvi(Im*, Rune);
|
||||||
void backko(Im*);
|
void backko(Im*);
|
||||||
void backvi(Im*);
|
void backvi(Im*);
|
||||||
void dictsend(Im*, Str*);
|
|
||||||
uvlong ownernew(void);
|
|
||||||
|
|
||||||
void srvthread(void*);
|
void srvthread(void*);
|
||||||
void ibusthread(void*);
|
void ibusthread(void*);
|
||||||
|
|||||||
5
ibus.c
5
ibus.c
@@ -30,7 +30,6 @@ struct Ictx
|
|||||||
{
|
{
|
||||||
DBusConnection *conn;
|
DBusConnection *conn;
|
||||||
char path[64];
|
char path[64];
|
||||||
uvlong owner;
|
|
||||||
int focused;
|
int focused;
|
||||||
Caret caret;
|
Caret caret;
|
||||||
};
|
};
|
||||||
@@ -282,7 +281,6 @@ newcontext(DBusConnection *conn, const char *path)
|
|||||||
if(contexts[i].conn == nil){
|
if(contexts[i].conn == nil){
|
||||||
memset(&contexts[i], 0, sizeof contexts[i]);
|
memset(&contexts[i], 0, sizeof contexts[i]);
|
||||||
contexts[i].conn = conn;
|
contexts[i].conn = conn;
|
||||||
contexts[i].owner = ownernew();
|
|
||||||
strncpy(contexts[i].path, path, sizeof contexts[i].path);
|
strncpy(contexts[i].path, path, sizeof contexts[i].path);
|
||||||
contexts[i].path[sizeof contexts[i].path-1] = '\0';
|
contexts[i].path[sizeof contexts[i].path-1] = '\0';
|
||||||
return &contexts[i];
|
return &contexts[i];
|
||||||
@@ -296,12 +294,11 @@ sendrequest(Ictx *ctx, int op, u32int ks, u32int mod, Keyres *res)
|
|||||||
Keyreq kr;
|
Keyreq kr;
|
||||||
|
|
||||||
memset(&kr, 0, sizeof kr);
|
memset(&kr, 0, sizeof kr);
|
||||||
kr.owner = ctx->owner;
|
kr.owner = ctx;
|
||||||
kr.op = op;
|
kr.op = op;
|
||||||
kr.ks = ks;
|
kr.ks = ks;
|
||||||
kr.mod = mod;
|
kr.mod = mod;
|
||||||
kr.caret = ctx->caret;
|
kr.caret = ctx->caret;
|
||||||
kr.want = op == Keypress;
|
|
||||||
kr.reply = replyc;
|
kr.reply = replyc;
|
||||||
chansend(keyc, &kr);
|
chansend(keyc, &kr);
|
||||||
chanrecv(replyc, res);
|
chanrecv(replyc, res);
|
||||||
|
|||||||
4
ipc.h
4
ipc.h
@@ -4,8 +4,8 @@
|
|||||||
/*
|
/*
|
||||||
* Request: [flags, modifiers, key byte 0, ..., key byte 3].
|
* Request: [flags, modifiers, key byte 0, ..., key byte 3].
|
||||||
* Flags request preedit and distinguish lifecycle reset from physical Escape.
|
* Flags request preedit and distinguish lifecycle reset from physical Escape.
|
||||||
* The server assigns the connection's owner generation; it is not sent on
|
* The server identifies the connection as the engine owner; that identity is
|
||||||
* the wire.
|
* not sent on the wire.
|
||||||
* Only Mmask modifier bits are retained.
|
* Only Mmask modifier bits are retained.
|
||||||
* Response: [eaten, commit-length-low, commit-length-high, commit...],
|
* Response: [eaten, commit-length-low, commit-length-high, commit...],
|
||||||
* followed, when requested, by
|
* followed, when requested, by
|
||||||
|
|||||||
14
srv.c
14
srv.c
@@ -11,7 +11,6 @@ typedef struct Client Client;
|
|||||||
struct Client
|
struct Client
|
||||||
{
|
{
|
||||||
int fd;
|
int fd;
|
||||||
uvlong owner;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
static int
|
static int
|
||||||
@@ -27,9 +26,8 @@ srvreadkey(int fd, Keyreq *kr)
|
|||||||
kr->op = ipcreqreset(req) ? Keyreset : Keypress;
|
kr->op = ipcreqreset(req) ? Keyreset : Keypress;
|
||||||
kr->ks = ks;
|
kr->ks = ks;
|
||||||
kr->mod = mod;
|
kr->mod = mod;
|
||||||
kr->want = want;
|
|
||||||
memset(&kr->caret, 0, sizeof kr->caret);
|
memset(&kr->caret, 0, sizeof kr->caret);
|
||||||
return 0;
|
return want;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
@@ -42,7 +40,7 @@ clientthread(void *arg)
|
|||||||
Keyres res;
|
Keyres res;
|
||||||
uchar out[Ipcmaxresp];
|
uchar out[Ipcmaxresp];
|
||||||
char commit[Maxutf], preedit[Maxutf];
|
char commit[Maxutf], preedit[Maxutf];
|
||||||
int n, ncommit, npreedit;
|
int n, ncommit, npreedit, want;
|
||||||
uchar token;
|
uchar token;
|
||||||
|
|
||||||
client = arg;
|
client = arg;
|
||||||
@@ -50,19 +48,18 @@ clientthread(void *arg)
|
|||||||
threadsetname("client %d", fd);
|
threadsetname("client %d", fd);
|
||||||
reply = chancreate(sizeof(Keyres), 0);
|
reply = chancreate(sizeof(Keyres), 0);
|
||||||
kr.reply = reply;
|
kr.reply = reply;
|
||||||
kr.owner = client->owner;
|
kr.owner = client;
|
||||||
while(srvreadkey(fd, &kr) == 0){
|
while((want = srvreadkey(fd, &kr)) >= 0){
|
||||||
chansend(keyc, &kr);
|
chansend(keyc, &kr);
|
||||||
chanrecv(reply, &res);
|
chanrecv(reply, &res);
|
||||||
ncommit = stoutf(&res.commit, commit, sizeof commit);
|
ncommit = stoutf(&res.commit, commit, sizeof commit);
|
||||||
npreedit = stoutf(&res.preedit, preedit, sizeof preedit);
|
npreedit = stoutf(&res.preedit, preedit, sizeof preedit);
|
||||||
n = ipcpackresp(out, sizeof out, res.eaten,
|
n = ipcpackresp(out, sizeof out, res.eaten,
|
||||||
commit, ncommit, preedit, npreedit, kr.want);
|
commit, ncommit, preedit, npreedit, want);
|
||||||
if(n < 0 || ipcsend(fd, out, n) < 0)
|
if(n < 0 || ipcsend(fd, out, n) < 0)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
kr.op = Keyrelease;
|
kr.op = Keyrelease;
|
||||||
kr.want = 0;
|
|
||||||
chansend(keyc, &kr);
|
chansend(keyc, &kr);
|
||||||
chanrecv(reply, &res);
|
chanrecv(reply, &res);
|
||||||
chanfree(reply);
|
chanfree(reply);
|
||||||
@@ -110,7 +107,6 @@ srvthread(void*)
|
|||||||
}
|
}
|
||||||
client = emalloc(sizeof *client);
|
client = emalloc(sizeof *client);
|
||||||
client->fd = fd;
|
client->fd = fd;
|
||||||
client->owner = ownernew();
|
|
||||||
if(proccreate(clientthread, client, 8192) < 0){
|
if(proccreate(clientthread, client, 8192) < 0){
|
||||||
chanrecv(clientc, &token);
|
chanrecv(clientc, &token);
|
||||||
close(fd);
|
close(fd);
|
||||||
|
|||||||
27
strans.c
27
strans.c
@@ -4,9 +4,7 @@
|
|||||||
static Im im;
|
static Im im;
|
||||||
static int popup = 0;
|
static int popup = 0;
|
||||||
static int visible = 0;
|
static int visible = 0;
|
||||||
static Lock ownerlock;
|
static void *activeowner;
|
||||||
static uvlong ownerctr;
|
|
||||||
static uvlong activeowner;
|
|
||||||
static Caret caret;
|
static Caret caret;
|
||||||
static void dictqmap(Im*);
|
static void dictqmap(Im*);
|
||||||
static void dictqjp(Im*);
|
static void dictqjp(Im*);
|
||||||
@@ -22,19 +20,6 @@ struct Search
|
|||||||
};
|
};
|
||||||
static Search search;
|
static Search search;
|
||||||
|
|
||||||
uvlong
|
|
||||||
ownernew(void)
|
|
||||||
{
|
|
||||||
uvlong n;
|
|
||||||
|
|
||||||
lock(&ownerlock);
|
|
||||||
n = ++ownerctr;
|
|
||||||
if(n == 0)
|
|
||||||
n = ++ownerctr;
|
|
||||||
unlock(&ownerlock);
|
|
||||||
return n;
|
|
||||||
}
|
|
||||||
|
|
||||||
Lang langs[] = {
|
Lang langs[] = {
|
||||||
{LangEN, nil, nil, nil, nil, nil, nil, nil},
|
{LangEN, nil, nil, nil, nil, nil, nil, nil},
|
||||||
{LangJP, "hira", "kanji", transmap, backjp, dictqjp, nil, nil},
|
{LangJP, "hira", "kanji", transmap, backjp, dictqjp, nil, nil},
|
||||||
@@ -155,7 +140,7 @@ reset(void)
|
|||||||
show();
|
show();
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
static void
|
||||||
dictsend(Im *im, Str *key)
|
dictsend(Im *im, Str *key)
|
||||||
{
|
{
|
||||||
Dictreq old, req;
|
Dictreq old, req;
|
||||||
@@ -792,7 +777,7 @@ init(void)
|
|||||||
im.l = getlang(LangEN);
|
im.l = getlang(LangEN);
|
||||||
memset(&search, 0, sizeof search);
|
memset(&search, 0, sizeof search);
|
||||||
memset(&caret, 0, sizeof caret);
|
memset(&caret, 0, sizeof caret);
|
||||||
activeowner = 0;
|
activeowner = nil;
|
||||||
visible = 0;
|
visible = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -814,7 +799,7 @@ imhandlekey(Keyreq *kr)
|
|||||||
case Keyrelease:
|
case Keyrelease:
|
||||||
if(kr->owner == activeowner){
|
if(kr->owner == activeowner){
|
||||||
reset();
|
reset();
|
||||||
activeowner = 0;
|
activeowner = nil;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case Keyreset:
|
case Keyreset:
|
||||||
@@ -827,7 +812,7 @@ imhandlekey(Keyreq *kr)
|
|||||||
show();
|
show();
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
default:
|
case Keypress:
|
||||||
res.eaten = 0;
|
res.eaten = 0;
|
||||||
if(meaningful(kr)){
|
if(meaningful(kr)){
|
||||||
if(kr->owner != activeowner){
|
if(kr->owner != activeowner){
|
||||||
@@ -840,7 +825,7 @@ imhandlekey(Keyreq *kr)
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
if(kr->want && kr->owner == activeowner){
|
if(kr->owner == activeowner){
|
||||||
if(search.lang)
|
if(search.lang)
|
||||||
res.preedit = search.text;
|
res.preedit = search.text;
|
||||||
else
|
else
|
||||||
|
|||||||
@@ -161,7 +161,7 @@ engine_dictionary_queue_latest_wins(struct ct *t)
|
|||||||
}
|
}
|
||||||
|
|
||||||
static Keyres
|
static Keyres
|
||||||
ownerrequestat(uvlong owner, int op, Rune key, u32int mod, Caret *caret)
|
ownerrequestat(void *owner, int op, Rune key, u32int mod, Caret *caret)
|
||||||
{
|
{
|
||||||
Channel *reply;
|
Channel *reply;
|
||||||
Keyreq req;
|
Keyreq req;
|
||||||
@@ -175,7 +175,6 @@ ownerrequestat(uvlong owner, int op, Rune key, u32int mod, Caret *caret)
|
|||||||
req.mod = mod;
|
req.mod = mod;
|
||||||
if(caret != nil)
|
if(caret != nil)
|
||||||
req.caret = *caret;
|
req.caret = *caret;
|
||||||
req.want = 1;
|
|
||||||
req.reply = reply;
|
req.reply = reply;
|
||||||
imhandlekey(&req);
|
imhandlekey(&req);
|
||||||
chanrecv(reply, &res);
|
chanrecv(reply, &res);
|
||||||
@@ -184,7 +183,7 @@ ownerrequestat(uvlong owner, int op, Rune key, u32int mod, Caret *caret)
|
|||||||
}
|
}
|
||||||
|
|
||||||
static Keyres
|
static Keyres
|
||||||
ownerrequest(uvlong owner, int op, Rune key, u32int mod)
|
ownerrequest(void *owner, int op, Rune key, u32int mod)
|
||||||
{
|
{
|
||||||
return ownerrequestat(owner, op, key, mod, nil);
|
return ownerrequestat(owner, op, key, mod, nil);
|
||||||
}
|
}
|
||||||
@@ -194,57 +193,75 @@ engine_active_owner_lifecycle(struct ct *t)
|
|||||||
{
|
{
|
||||||
Keyres res;
|
Keyres res;
|
||||||
Str shown;
|
Str shown;
|
||||||
uvlong a, b, c;
|
char a, b, c;
|
||||||
|
|
||||||
a = ownernew();
|
|
||||||
b = ownernew();
|
|
||||||
c = ownernew();
|
|
||||||
CT_CHECK(t, a != 0 && b != 0 && c != 0);
|
|
||||||
CT_CHECK(t, a != b && b != c && a != c);
|
|
||||||
init();
|
init();
|
||||||
im.l = getlang(LangJP);
|
im.l = getlang(LangJP);
|
||||||
res = ownerrequest(a, Keypress, 'k', 0);
|
res = ownerrequest(&a, Keypress, 'k', 0);
|
||||||
CT_CHECK(t, res.eaten);
|
CT_CHECK(t, res.eaten);
|
||||||
res = ownerrequest(a, Keypress, 'a', 0);
|
res = ownerrequest(&a, Keypress, 'a', 0);
|
||||||
checkstr(t, "first owner preedit", "か", &res.preedit);
|
checkstr(t, "first owner preedit", "か", &res.preedit);
|
||||||
CT_EQ_UINT(t, a, activeowner);
|
CT_EQ_PTR(t, &a, activeowner);
|
||||||
|
|
||||||
res = ownerrequest(b, Keypress, 'n', 0);
|
res = ownerrequest(&b, Keypress, 'n', 0);
|
||||||
checkstr(t, "takeover resets old preedit", "ん", &res.preedit);
|
checkstr(t, "takeover resets old preedit", "ん", &res.preedit);
|
||||||
CT_EQ_UINT(t, b, activeowner);
|
CT_EQ_PTR(t, &b, activeowner);
|
||||||
res = ownerrequest(a, Keyreset, 0, 0);
|
res = ownerrequest(&a, Keyreset, 0, 0);
|
||||||
CT_EQ_INT(t, 0, res.preedit.n);
|
CT_EQ_INT(t, 0, res.preedit.n);
|
||||||
shown = shownpre(&im);
|
shown = shownpre(&im);
|
||||||
checkstr(t, "stale reset preserves owner", "ん", &shown);
|
checkstr(t, "stale reset preserves owner", "ん", &shown);
|
||||||
CT_EQ_UINT(t, b, activeowner);
|
CT_EQ_PTR(t, &b, activeowner);
|
||||||
|
|
||||||
res = ownerrequest(b, Keypress, 'y', 0);
|
res = ownerrequest(&b, Keypress, 'y', 0);
|
||||||
res = ownerrequest(b, Keypress, 'a', 0);
|
res = ownerrequest(&b, Keypress, 'a', 0);
|
||||||
checkstr(t, "current owner continues", "にゃ", &res.preedit);
|
checkstr(t, "current owner continues", "にゃ", &res.preedit);
|
||||||
ownerrequest(a, Keyrelease, 0, 0);
|
ownerrequest(&a, Keyrelease, 0, 0);
|
||||||
shown = shownpre(&im);
|
shown = shownpre(&im);
|
||||||
checkstr(t, "stale release preserves owner", "にゃ", &shown);
|
checkstr(t, "stale release preserves owner", "にゃ", &shown);
|
||||||
CT_EQ_UINT(t, b, activeowner);
|
CT_EQ_PTR(t, &b, activeowner);
|
||||||
|
|
||||||
ownerrequest(b, Keyrelease, 0, 0);
|
ownerrequest(&b, Keyrelease, 0, 0);
|
||||||
CT_EQ_UINT(t, 0, activeowner);
|
CT_EQ_PTR(t, nil, activeowner);
|
||||||
CT_EQ_INT(t, 0, im.pre.n);
|
CT_EQ_INT(t, 0, im.pre.n);
|
||||||
CT_EQ_INT(t, 0, im.raw.n);
|
CT_EQ_INT(t, 0, im.raw.n);
|
||||||
ownerrequest(c, Keypress, Kmodfirst, 0);
|
ownerrequest(&c, Keypress, Kmodfirst, 0);
|
||||||
CT_EQ_UINT(t, 0, activeowner);
|
CT_EQ_PTR(t, nil, activeowner);
|
||||||
res = ownerrequest(c, Keypress, 'k', 0);
|
res = ownerrequest(&c, Keypress, 'k', 0);
|
||||||
CT_EQ_UINT(t, c, activeowner);
|
CT_EQ_PTR(t, &c, activeowner);
|
||||||
checkstr(t, "next owner first key", "k", &res.preedit);
|
checkstr(t, "next owner first key", "k", &res.preedit);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
engine_active_owner_reset(struct ct *t)
|
||||||
|
{
|
||||||
|
Caret at;
|
||||||
|
Keyres res;
|
||||||
|
char owner;
|
||||||
|
|
||||||
|
memset(&at, 0, sizeof at);
|
||||||
|
at.valid = 1;
|
||||||
|
at.x = 10;
|
||||||
|
at.y = 20;
|
||||||
|
at.h = 14;
|
||||||
|
init();
|
||||||
|
im.l = getlang(LangJP);
|
||||||
|
ownerrequestat(&owner, Keypress, 'k', 0, &at);
|
||||||
|
res = ownerrequest(&owner, Keypress, 'a', 0);
|
||||||
|
checkstr(t, "preedit before reset", "か", &res.preedit);
|
||||||
|
res = ownerrequest(&owner, Keyreset, 0, 0);
|
||||||
|
CT_EQ_PTR(t, &owner, activeowner);
|
||||||
|
CT_EQ_INT(t, 0, res.preedit.n);
|
||||||
|
CT_CHECK(t, !caret.valid);
|
||||||
|
res = ownerrequest(&owner, Keypress, 'n', 0);
|
||||||
|
checkstr(t, "same owner after reset", "ん", &res.preedit);
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
engine_active_owner_caret(struct ct *t)
|
engine_active_owner_caret(struct ct *t)
|
||||||
{
|
{
|
||||||
Caret a, moved;
|
Caret a, moved;
|
||||||
uvlong one, two;
|
char one, two;
|
||||||
|
|
||||||
one = ownernew();
|
|
||||||
two = ownernew();
|
|
||||||
memset(&a, 0, sizeof a);
|
memset(&a, 0, sizeof a);
|
||||||
a.valid = 1;
|
a.valid = 1;
|
||||||
a.x = 10;
|
a.x = 10;
|
||||||
@@ -254,15 +271,15 @@ engine_active_owner_caret(struct ct *t)
|
|||||||
moved.x = 80;
|
moved.x = 80;
|
||||||
init();
|
init();
|
||||||
im.l = getlang(LangJP);
|
im.l = getlang(LangJP);
|
||||||
ownerrequestat(one, Keypress, 'k', 0, &a);
|
ownerrequestat(&one, Keypress, 'k', 0, &a);
|
||||||
CT_CHECK(t, caret.valid);
|
CT_CHECK(t, caret.valid);
|
||||||
CT_EQ_INT(t, 10, caret.x);
|
CT_EQ_INT(t, 10, caret.x);
|
||||||
ownerrequestat(two, Keycaret, 0, 0, &moved);
|
ownerrequestat(&two, Keycaret, 0, 0, &moved);
|
||||||
CT_EQ_INT(t, 10, caret.x);
|
CT_EQ_INT(t, 10, caret.x);
|
||||||
ownerrequestat(one, Keycaret, 0, 0, &moved);
|
ownerrequestat(&one, Keycaret, 0, 0, &moved);
|
||||||
CT_EQ_INT(t, 80, caret.x);
|
CT_EQ_INT(t, 80, caret.x);
|
||||||
ownerrequest(two, Keypress, 'n', 0);
|
ownerrequest(&two, Keypress, 'n', 0);
|
||||||
CT_EQ_UINT(t, two, activeowner);
|
CT_EQ_PTR(t, &two, activeowner);
|
||||||
CT_CHECK(t, !caret.valid);
|
CT_CHECK(t, !caret.valid);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1430,7 +1447,8 @@ engine_randomized_stress(struct ct *t)
|
|||||||
Keyres res;
|
Keyres res;
|
||||||
Caret pos;
|
Caret pos;
|
||||||
u32int rnd, mod;
|
u32int rnd, mod;
|
||||||
uvlong owners[3], owner;
|
char contexts[3];
|
||||||
|
void *owner, *owners[3];
|
||||||
int i, j, op;
|
int i, j, op;
|
||||||
|
|
||||||
vi = getlang(LangVI);
|
vi = getlang(LangVI);
|
||||||
@@ -1439,9 +1457,9 @@ engine_randomized_stress(struct ct *t)
|
|||||||
vimap = vi->map;
|
vimap = vi->map;
|
||||||
vi->map = testvi.map;
|
vi->map = testvi.map;
|
||||||
emojibegin(&f, 0);
|
emojibegin(&f, 0);
|
||||||
owners[0] = ownernew();
|
owners[0] = &contexts[0];
|
||||||
owners[1] = ownernew();
|
owners[1] = &contexts[1];
|
||||||
owners[2] = ownernew();
|
owners[2] = &contexts[2];
|
||||||
rnd = 0x5eed1234U;
|
rnd = 0x5eed1234U;
|
||||||
for(i = 0; i < 16000; i++){
|
for(i = 0; i < 16000; i++){
|
||||||
rnd = stressrand(&rnd);
|
rnd = stressrand(&rnd);
|
||||||
@@ -1506,7 +1524,7 @@ engine_randomized_stress(struct ct *t)
|
|||||||
i = 16000;
|
i = 16000;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
if(activeowner != 0 && activeowner != owners[0] &&
|
if(activeowner != nil && activeowner != owners[0] &&
|
||||||
activeowner != owners[1] && activeowner != owners[2]){
|
activeowner != owners[1] && activeowner != owners[2]){
|
||||||
CT_ERRORF(t, "unknown active owner after stress operation %d", i);
|
CT_ERRORF(t, "unknown active owner after stress operation %d", i);
|
||||||
break;
|
break;
|
||||||
|
|||||||
@@ -34,6 +34,7 @@ void engine_selects_visible_candidate(struct ct*);
|
|||||||
void engine_candidate_shortcut_modifiers(struct ct*);
|
void engine_candidate_shortcut_modifiers(struct ct*);
|
||||||
void engine_dictionary_queue_latest_wins(struct ct*);
|
void engine_dictionary_queue_latest_wins(struct ct*);
|
||||||
void engine_active_owner_lifecycle(struct ct*);
|
void engine_active_owner_lifecycle(struct ct*);
|
||||||
|
void engine_active_owner_reset(struct ct*);
|
||||||
void engine_active_owner_caret(struct ct*);
|
void engine_active_owner_caret(struct ct*);
|
||||||
void engine_commit_contract(struct ct*);
|
void engine_commit_contract(struct ct*);
|
||||||
void engine_language_switch_state(struct ct*);
|
void engine_language_switch_state(struct ct*);
|
||||||
|
|||||||
@@ -88,6 +88,7 @@ static const struct ct_test tests[] = {
|
|||||||
{ "engine/candidate-shortcut-modifiers", engine_candidate_shortcut_modifiers },
|
{ "engine/candidate-shortcut-modifiers", engine_candidate_shortcut_modifiers },
|
||||||
{ "engine/dictionary-queue-latest", engine_dictionary_queue_latest_wins },
|
{ "engine/dictionary-queue-latest", engine_dictionary_queue_latest_wins },
|
||||||
{ "engine/active-owner-lifecycle", engine_active_owner_lifecycle },
|
{ "engine/active-owner-lifecycle", engine_active_owner_lifecycle },
|
||||||
|
{ "engine/active-owner-reset", engine_active_owner_reset },
|
||||||
{ "engine/active-owner-caret", engine_active_owner_caret },
|
{ "engine/active-owner-caret", engine_active_owner_caret },
|
||||||
{ "engine/commit-contract", engine_commit_contract },
|
{ "engine/commit-contract", engine_commit_contract },
|
||||||
{ "engine/language-switch-state", engine_language_switch_state },
|
{ "engine/language-switch-state", engine_language_switch_state },
|
||||||
|
|||||||
Reference in New Issue
Block a user