Clean up progress callbacks in fsm/psm machinery
- Move notifications from fsm to psm side for sanity and symmetry, psm already has members to hold the callback state. - Replace PSM_NOTIFY "state" with a helper function that both fsm and psm itself use (except for error callbacks which are a bit different) - Init psm->total early, this doesn't change and can now be used to refer to "all done" value whatever it happens to be, instead of magic "100" values etc. - Packages with no files are now handled through the same path as everything else from progress reporting pov, we just skip calls to fsm if there are no files. - Issue stop callbacks for install as well. While INST_CLOSE_FILE can be (and is currently) used to detect this condition, its conceptually an entirely different thing. - Fix erasure callback parameters, they were reversed (starting from total and ending with 0, ehh...)
This commit is contained in:
parent
ff0ece3f6b
commit
72bd2de21e
15
lib/fsm.c
15
lib/fsm.c
|
@ -627,12 +627,6 @@ int fsmSetup(FSM_t fsm, fileStage goal,
|
|||
fsm->digestalgo = rpmfiDigestAlgo(fi);
|
||||
fsm->psm = psm;
|
||||
|
||||
if (fsm->goal == FSM_PKGINSTALL) {
|
||||
fsm->archivePos = 0;
|
||||
rpmtsNotify(ts, te, RPMCALLBACK_INST_START,
|
||||
fsm->archivePos, fi->archiveSize);
|
||||
}
|
||||
|
||||
fsm->archiveSize = archiveSize;
|
||||
if (fsm->archiveSize)
|
||||
*fsm->archiveSize = 0;
|
||||
|
@ -1891,14 +1885,7 @@ if (!(fsm->mapFlags & CPIO_ALL_HARDLINKS)) break;
|
|||
break;
|
||||
case FSM_NOTIFY: /* XXX move from fsm to psm -> tsm */
|
||||
if (fsm->goal == FSM_PKGINSTALL) {
|
||||
rpmts ts = fsmGetTs(fsm);
|
||||
rpmte te = fsmGetTe(fsm);
|
||||
rpmfi fi = fsmGetFi(fsm);
|
||||
if (fsm->cpioPos > fsm->archivePos) {
|
||||
fsm->archivePos = fsm->cpioPos;
|
||||
rpmtsNotify(ts, te, RPMCALLBACK_INST_PROGRESS,
|
||||
fsm->archivePos, fi->archiveSize);
|
||||
}
|
||||
rpmpsmNotify(fsm->psm, RPMCALLBACK_INST_PROGRESS, fsm->cpioPos);
|
||||
}
|
||||
break;
|
||||
case FSM_UNDO:
|
||||
|
|
|
@ -225,6 +225,8 @@ int fsmTeardown(FSM_t fsm);
|
|||
RPM_GNUC_INTERNAL
|
||||
int fsmNext(FSM_t fsm, fileStage nstage);
|
||||
|
||||
RPM_GNUC_INTERNAL
|
||||
void rpmpsmNotify(rpmpsm psm, int what, rpm_loff_t amount);
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
|
97
lib/psm.c
97
lib/psm.c
|
@ -37,7 +37,6 @@ typedef enum pkgStage_e {
|
|||
PSM_FINI = 6,
|
||||
|
||||
PSM_CREATE = 17,
|
||||
PSM_NOTIFY = 22,
|
||||
PSM_DESTROY = 23,
|
||||
|
||||
PSM_SCRIPT = 53,
|
||||
|
@ -655,6 +654,25 @@ static rpmpsm rpmpsmNew(rpmts ts, rpmte te)
|
|||
return psm;
|
||||
}
|
||||
|
||||
void rpmpsmNotify(rpmpsm psm, int what, rpm_loff_t amount)
|
||||
{
|
||||
if (psm) {
|
||||
int changed = 0;
|
||||
if (amount > psm->amount) {
|
||||
psm->amount = amount;
|
||||
changed = 1;
|
||||
}
|
||||
if (what && what != psm->what) {
|
||||
psm->what = what;
|
||||
changed = 1;
|
||||
}
|
||||
if (changed) {
|
||||
rpmtsNotify(psm->ts, psm->te, psm->what, psm->amount, psm->total);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static int runFsm(rpmpsm psm, FD_t payload)
|
||||
{
|
||||
int sc, ec;
|
||||
|
@ -733,6 +751,9 @@ static rpmRC rpmpsmStage(rpmpsm psm, pkgStage stage)
|
|||
if (psm->goal == PKG_INSTALL) {
|
||||
psm->scriptArg = psm->npkgs_installed + 1;
|
||||
|
||||
psm->amount = 0;
|
||||
psm->total = fi->archiveSize ? fi->archiveSize : 100;
|
||||
|
||||
/* HACK: reinstall abuses te instance to remove old header */
|
||||
if (rpmtsFilterFlags(ts) & RPMPROB_FILTER_REPLACEPKG)
|
||||
markReplacedInstance(ts, psm->te);
|
||||
|
@ -756,6 +777,9 @@ static rpmRC rpmpsmStage(rpmpsm psm, pkgStage stage)
|
|||
}
|
||||
if (psm->goal == PKG_ERASE) {
|
||||
psm->scriptArg = psm->npkgs_installed - 1;
|
||||
|
||||
psm->amount = 0;
|
||||
psm->total = rpmfiFC(fi) ? rpmfiFC(fi) : 100;
|
||||
}
|
||||
break;
|
||||
case PSM_PRE:
|
||||
|
@ -801,33 +825,29 @@ static rpmRC rpmpsmStage(rpmpsm psm, pkgStage stage)
|
|||
break;
|
||||
case PSM_PROCESS:
|
||||
if (psm->goal == PKG_INSTALL) {
|
||||
FD_t payload = NULL;
|
||||
int fsmrc;
|
||||
int fsmrc = 0;
|
||||
|
||||
if (rpmtsFlags(ts) & RPMTRANS_FLAG_JUSTDB) break;
|
||||
|
||||
/* XXX Synthesize callbacks for packages with no files. */
|
||||
if (rpmfiFC(fi) <= 0) {
|
||||
rpmtsNotify(ts, psm->te, RPMCALLBACK_INST_START, 0, 100);
|
||||
rpmtsNotify(ts, psm->te, RPMCALLBACK_INST_PROGRESS, 100, 100);
|
||||
break;
|
||||
rpmpsmNotify(psm, RPMCALLBACK_INST_START, 0);
|
||||
/* make sure first progress call gets made */
|
||||
rpmpsmNotify(psm, RPMCALLBACK_INST_PROGRESS, 0);
|
||||
|
||||
if (rpmfiFC(fi) > 0) {
|
||||
FD_t payload = rpmtePayload(psm->te);
|
||||
if (payload == NULL) {
|
||||
rc = RPMRC_FAIL;
|
||||
break;
|
||||
}
|
||||
|
||||
fsmrc = runFsm(psm, payload);
|
||||
|
||||
Fclose(payload);
|
||||
}
|
||||
|
||||
payload = rpmtePayload(psm->te);
|
||||
if (payload == NULL) {
|
||||
rc = RPMRC_FAIL;
|
||||
break;
|
||||
}
|
||||
|
||||
fsmrc = runFsm(psm, payload);
|
||||
|
||||
Fclose(payload);
|
||||
|
||||
/* XXX make sure progress is closed out */
|
||||
psm->what = RPMCALLBACK_INST_PROGRESS;
|
||||
psm->amount = (fi->archiveSize ? fi->archiveSize : 100);
|
||||
psm->total = psm->amount;
|
||||
rpmpsmNext(psm, PSM_NOTIFY);
|
||||
/* XXX make sure progress reaches 100% */
|
||||
rpmpsmNotify(psm, 0, psm->total);
|
||||
rpmpsmNotify(psm, RPMCALLBACK_INST_STOP, psm->total);
|
||||
|
||||
if (fsmrc) {
|
||||
rpmlog(RPMLOG_ERR,
|
||||
|
@ -843,30 +863,20 @@ static rpmRC rpmpsmStage(rpmpsm psm, pkgStage stage)
|
|||
}
|
||||
}
|
||||
if (psm->goal == PKG_ERASE) {
|
||||
int fc = rpmfiFC(fi);
|
||||
|
||||
if (rpmtsFlags(ts) & RPMTRANS_FLAG_JUSTDB) break;
|
||||
|
||||
/* XXX Synthesize callbacks for packages with no files. */
|
||||
if (rpmfiFC(fi) <= 0) {
|
||||
rpmtsNotify(ts, psm->te, RPMCALLBACK_UNINST_START, 0, 100);
|
||||
rpmtsNotify(ts, psm->te, RPMCALLBACK_UNINST_STOP, 0, 100);
|
||||
break;
|
||||
}
|
||||
|
||||
psm->what = RPMCALLBACK_UNINST_START;
|
||||
psm->amount = fc; /* XXX W2DO? looks wrong. */
|
||||
psm->total = fc;
|
||||
rpmpsmNext(psm, PSM_NOTIFY);
|
||||
rpmpsmNotify(psm, RPMCALLBACK_UNINST_START, 0);
|
||||
/* make sure first progress call gets made */
|
||||
rpmpsmNotify(psm, RPMCALLBACK_INST_PROGRESS, 0);
|
||||
|
||||
/* XXX should't we log errors from here? */
|
||||
rc = runFsm(psm, NULL) ? RPMRC_FAIL : RPMRC_OK;
|
||||
|
||||
psm->what = RPMCALLBACK_UNINST_STOP;
|
||||
psm->amount = 0; /* XXX W2DO? looks wrong. */
|
||||
psm->total = fc;
|
||||
rpmpsmNext(psm, PSM_NOTIFY);
|
||||
if (rpmfiFC(fi) > 0) {
|
||||
rc = runFsm(psm, NULL) ? RPMRC_FAIL : RPMRC_OK;
|
||||
}
|
||||
|
||||
/* XXX make sure progress reaches 100% */
|
||||
rpmpsmNotify(psm, 0, psm->total);
|
||||
rpmpsmNotify(psm, RPMCALLBACK_UNINST_STOP, psm->total);
|
||||
}
|
||||
break;
|
||||
case PSM_POST:
|
||||
|
@ -962,9 +972,6 @@ static rpmRC rpmpsmStage(rpmpsm psm, pkgStage stage)
|
|||
|
||||
case PSM_CREATE:
|
||||
break;
|
||||
case PSM_NOTIFY:
|
||||
rpmtsNotify(ts, psm->te, psm->what, psm->amount, psm->total);
|
||||
break;
|
||||
case PSM_DESTROY:
|
||||
break;
|
||||
case PSM_SCRIPT: /* Run current package scriptlets. */
|
||||
|
|
Loading…
Reference in New Issue