Make AVFS resilient against failing back calls
This commit is contained in:
parent
8a266a478e
commit
7db039347a
@ -24,6 +24,7 @@ struct fproc *rfp;
|
||||
|
||||
transid = rfp->fp_wtid + VFS_TRANSID;
|
||||
rfp->fp_sendrec->m_type = TRNS_ADD_ID(rfp->fp_sendrec->m_type, transid);
|
||||
rfp->fp_task = vmp->m_fs_e;
|
||||
if ((r = asynsend3(vmp->m_fs_e, rfp->fp_sendrec, AMF_NOREPLY)) != OK) {
|
||||
printf("VFS: sendmsg: error sending message. "
|
||||
"FS_e: %d req_nr: %d err: %d\n", vmp->m_fs_e,
|
||||
|
@ -257,6 +257,7 @@ PRIVATE void *do_fs_reply(struct job *job)
|
||||
}
|
||||
|
||||
*rfp->fp_sendrec = m_in;
|
||||
rfp->fp_task = NONE;
|
||||
vmp->m_comm.c_cur_reqs--; /* We've got our reply, make room for others */
|
||||
|
||||
worker_signal(worker_get(rfp->fp_wtid));/* Continue this worker thread */
|
||||
@ -342,7 +343,7 @@ PRIVATE void *do_pending_pipe(void *arg)
|
||||
fp->fp_buffer, fp->fp_nbytes);
|
||||
|
||||
if (r != SUSPEND) /* Do we have results to report? */
|
||||
reply(who_e, r);
|
||||
(void) reply(who_e, r);
|
||||
|
||||
unlock_filp(f);
|
||||
|
||||
@ -376,8 +377,10 @@ PUBLIC void *do_dummy(void *arg)
|
||||
*===========================================================================*/
|
||||
PRIVATE void *do_work(void *arg)
|
||||
{
|
||||
int error;
|
||||
int error, i;
|
||||
struct job my_job;
|
||||
struct fproc *rfp;
|
||||
struct vmnt *vmp;
|
||||
|
||||
my_job = *((struct job *) arg);
|
||||
fp = my_job.j_fp;
|
||||
@ -422,14 +425,24 @@ PRIVATE void *do_work(void *arg)
|
||||
/* Copy the results back to the user and send reply. */
|
||||
if (error != SUSPEND) {
|
||||
if (deadlock_resolving) {
|
||||
struct vmnt *vmp;
|
||||
if ((vmp = find_vmnt(who_e)) != NULL)
|
||||
vmp->m_flags &= ~VMNT_BACKCALL;
|
||||
|
||||
if (fp->fp_wtid == dl_worker.w_tid)
|
||||
deadlock_resolving = 0;
|
||||
}
|
||||
reply(who_e, error );
|
||||
if (reply(who_e, error) != OK) {
|
||||
if ((vmp = find_vmnt(who_e)) != NULL) {
|
||||
for (i = 0; i < NR_PROCS; i++) {
|
||||
rfp = &fproc[i];
|
||||
if (rfp->fp_task == vmp->m_fs_e) {
|
||||
/* We found a process waiting for a
|
||||
* reply from non-responsive FS */
|
||||
worker_stop(worker_get(rfp->fp_wtid));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
thread_cleanup(fp);
|
||||
@ -751,7 +764,7 @@ PRIVATE void get_work()
|
||||
/*===========================================================================*
|
||||
* reply *
|
||||
*===========================================================================*/
|
||||
PUBLIC void reply(whom, result)
|
||||
PUBLIC int reply(whom, result)
|
||||
int whom; /* process to reply to */
|
||||
int result; /* result of the call (usually OK or error #) */
|
||||
{
|
||||
@ -762,8 +775,8 @@ int result; /* result of the call (usually OK or error #) */
|
||||
r = sendnb(whom, &m_out);
|
||||
if (r != OK) {
|
||||
printf("VFS: couldn't send reply %d to %d: %d\n", result, whom, r);
|
||||
panic("Yikes %d", call_nr);
|
||||
}
|
||||
return(r);
|
||||
}
|
||||
|
||||
/*===========================================================================*
|
||||
@ -895,7 +908,8 @@ PRIVATE void service_pm()
|
||||
|
||||
break;
|
||||
case PM_SETGROUPS:
|
||||
pm_setgroups(m_in.PM_PROC, m_in.PM_GROUP_NO, m_in.PM_GROUP_ADDR);
|
||||
pm_setgroups(m_in.PM_PROC, m_in.PM_GROUP_NO,
|
||||
(gid_t *) m_in.PM_GROUP_ADDR);
|
||||
|
||||
m_out.m_type = PM_SETGROUPS_REPLY;
|
||||
m_out.PM_PROC = m_in.PM_PROC;
|
||||
|
@ -222,8 +222,11 @@ char mount_label[LABEL_MAX] )
|
||||
} else
|
||||
r = EBUSY;
|
||||
|
||||
if (vp != NULL)
|
||||
if (vp != NULL) {
|
||||
/* Quickly unlock to allow back calls (from e.g. FUSE) to
|
||||
* relock */
|
||||
unlock_vmnt(parent_vmp);
|
||||
}
|
||||
|
||||
if (r != OK) {
|
||||
if (vp != NULL) {
|
||||
|
@ -116,7 +116,7 @@ _PROTOTYPE( void lock_revive, (void) );
|
||||
|
||||
/* main.c */
|
||||
_PROTOTYPE( int main, (void) );
|
||||
_PROTOTYPE( void reply, (int whom, int result) );
|
||||
_PROTOTYPE( int reply, (int whom, int result) );
|
||||
_PROTOTYPE( void lock_proc, (struct fproc *rfp, int force_lock) );
|
||||
_PROTOTYPE( void unlock_proc, (struct fproc *rfp) );
|
||||
_PROTOTYPE( void *do_dummy, (void *arg) );
|
||||
@ -366,8 +366,9 @@ _PROTOTYPE( struct worker_thread *worker_get, (thread_t worker_tid) );
|
||||
_PROTOTYPE( struct job *worker_getjob, (thread_t worker_tid) );
|
||||
_PROTOTYPE( void worker_init, (struct worker_thread *worker) );
|
||||
_PROTOTYPE( struct worker_thread *worker_self, (void) );
|
||||
_PROTOTYPE( void worker_start, (void *(*func)(void *arg)) );
|
||||
_PROTOTYPE( void worker_signal, (struct worker_thread *worker) );
|
||||
_PROTOTYPE( void worker_start, (void *(*func)(void *arg)) );
|
||||
_PROTOTYPE( void worker_stop, (struct worker_thread *worker) );
|
||||
_PROTOTYPE( void worker_wait, (void) );
|
||||
_PROTOTYPE( void sys_worker_start, (void *(*func)(void *arg)) );
|
||||
_PROTOTYPE( void dl_worker_start, (void *(*func)(void *arg)) );
|
||||
|
@ -177,9 +177,11 @@ PUBLIC int lock_vnode(struct vnode *vp, tll_access_t locktype)
|
||||
*===========================================================================*/
|
||||
PUBLIC void unlock_vnode(struct vnode *vp)
|
||||
{
|
||||
#if LOCK_DEBUG
|
||||
int i;
|
||||
register struct vnode *rvp;
|
||||
struct worker_thread *w;
|
||||
#endif
|
||||
ASSERTVP(vp);
|
||||
|
||||
#if LOCK_DEBUG
|
||||
|
@ -286,6 +286,16 @@ PUBLIC void worker_signal(struct worker_thread *worker)
|
||||
worker_wake(worker);
|
||||
}
|
||||
|
||||
/*===========================================================================*
|
||||
* worker_stop *
|
||||
*===========================================================================*/
|
||||
PUBLIC void worker_stop(struct worker_thread *worker)
|
||||
{
|
||||
ASSERTW(worker); /* Make sure we have a valid thread */
|
||||
worker->w_job.j_m_in.m_type = -EIO;
|
||||
worker_wake(worker);
|
||||
}
|
||||
|
||||
/*===========================================================================*
|
||||
* worker_self *
|
||||
*===========================================================================*/
|
||||
|
Loading…
x
Reference in New Issue
Block a user