use linker to align fpu state save area

This commit is contained in:
Ben Gras
2012-04-19 15:06:47 +02:00
parent 093c949274
commit a149be43fc
11 changed files with 45 additions and 81 deletions

View File

@@ -27,7 +27,7 @@ int do_fork(struct proc * caller, message * m_ptr)
/* Handle sys_fork(). PR_ENDPT has forked. The child is PR_SLOT. */
#if (_MINIX_CHIP == _CHIP_INTEL)
reg_t old_ldt_sel;
void *old_fpu_save_area_p;
char *old_fpu_save_area_p;
#endif
register struct proc *rpc; /* child process pointer */
struct proc *rpp; /* parent process pointer */
@@ -59,16 +59,14 @@ int do_fork(struct proc * caller, message * m_ptr)
gen = _ENDPOINT_G(rpc->p_endpoint);
#if (_MINIX_CHIP == _CHIP_INTEL)
old_ldt_sel = rpc->p_seg.p_ldt_sel; /* backup local descriptors */
old_fpu_save_area_p = rpc->p_fpu_state.fpu_save_area_p;
old_fpu_save_area_p = rpc->p_seg.fpu_state;
#endif
*rpc = *rpp; /* copy 'proc' struct */
#if (_MINIX_CHIP == _CHIP_INTEL)
rpc->p_seg.p_ldt_sel = old_ldt_sel; /* restore descriptors */
rpc->p_fpu_state.fpu_save_area_p = old_fpu_save_area_p;
rpc->p_seg.fpu_state = old_fpu_save_area_p;
if(proc_used_fpu(rpp))
memcpy(rpc->p_fpu_state.fpu_save_area_p,
rpp->p_fpu_state.fpu_save_area_p,
FPU_XFP_SIZE);
memcpy(rpc->p_seg.fpu_state, rpp->p_seg.fpu_state, FPU_XFP_SIZE);
#endif
if(++gen >= _ENDPOINT_MAX_GENERATION) /* increase generation */
gen = 1; /* generation number wraparound */

View File

@@ -45,8 +45,7 @@ int do_getmcontext(struct proc * caller, message * m_ptr)
/* make sure that the FPU context is saved into proc structure first */
save_fpu(rp);
mc.mc_fpu_flags = rp->p_misc_flags & MF_FPU_INITIALIZED;
memcpy(&(mc.mc_fpu_state), rp->p_fpu_state.fpu_save_area_p,
FPU_XFP_SIZE);
memcpy(&(mc.mc_fpu_state), rp->p_seg.fpu_state, FPU_XFP_SIZE);
}
#endif
@@ -84,8 +83,7 @@ int do_setmcontext(struct proc * caller, message * m_ptr)
/* Copy FPU state */
if (mc.mc_fpu_flags & MF_FPU_INITIALIZED) {
rp->p_misc_flags |= MF_FPU_INITIALIZED;
memcpy(rp->p_fpu_state.fpu_save_area_p, &(mc.mc_fpu_state),
FPU_XFP_SIZE);
memcpy(rp->p_seg.fpu_state, &(mc.mc_fpu_state), FPU_XFP_SIZE);
} else
rp->p_misc_flags &= ~MF_FPU_INITIALIZED;
/* force reloading FPU in either case */

View File

@@ -55,8 +55,7 @@ int do_sigreturn(struct proc * caller, message * m_ptr)
#if (_MINIX_CHIP == _CHIP_INTEL)
if(sc.sc_flags & MF_FPU_INITIALIZED)
{
memcpy(rp->p_fpu_state.fpu_save_area_p, &sc.sc_fpu_state,
FPU_XFP_SIZE);
memcpy(rp->p_seg.fpu_state, &sc.sc_fpu_state, FPU_XFP_SIZE);
rp->p_misc_flags |= MF_FPU_INITIALIZED; /* Restore math usage flag. */
/* force reloading FPU */
release_fpu(rp);

View File

@@ -46,8 +46,7 @@ int do_sigsend(struct proc * caller, message * m_ptr)
if(proc_used_fpu(rp)) {
/* save the FPU context before saving it to the sig context */
save_fpu(rp);
memcpy(&sc.sc_fpu_state, rp->p_fpu_state.fpu_save_area_p,
FPU_XFP_SIZE);
memcpy(&sc.sc_fpu_state, rp->p_seg.fpu_state, FPU_XFP_SIZE);
}
#endif

View File

@@ -22,8 +22,6 @@
static void adjust_proc_slot(struct proc *rp, struct proc *from_rp);
static void adjust_priv_slot(struct priv *privp, struct priv
*from_privp);
static void swap_fpu_state(struct proc *a_rp, struct proc *b_orig_rp,
struct proc *b_copy_rp);
static void swap_proc_slot_pointer(struct proc **rpp, struct proc
*src_rp, struct proc *dst_rp);
@@ -110,10 +108,6 @@ int do_update(struct proc * caller, message * m_ptr)
adjust_priv_slot(priv(src_rp), &orig_src_priv);
adjust_priv_slot(priv(dst_rp), &orig_dst_priv);
/* Swap FPU state. Can only be done after adjusting the process slots. */
swap_fpu_state(src_rp, dst_rp, &orig_dst_proc);
swap_fpu_state(dst_rp, src_rp, &orig_src_proc);
/* Swap global process slot addresses. */
swap_proc_slot_pointer(get_cpulocal_var_ptr(ptproc), src_rp, dst_rp);
@@ -152,11 +146,6 @@ static void adjust_proc_slot(struct proc *rp, struct proc *from_rp)
priv(rp)->s_proc_nr = from_rp->p_nr;
rp->p_caller_q = from_rp->p_caller_q;
#if (_MINIX_CHIP == _CHIP_INTEL)
/* Preserve FPU pointer. */
rp->p_fpu_state.fpu_save_area_p = from_rp->p_fpu_state.fpu_save_area_p;
#endif
/* preserve scheduling */
rp->p_scheduler = from_rp->p_scheduler;
#ifdef CONFIG_SMP
@@ -179,26 +168,6 @@ static void adjust_priv_slot(struct priv *privp, struct priv *from_privp)
privp->s_alarm_timer = from_privp->s_alarm_timer;
}
/*===========================================================================*
* swap_fpu_state *
*===========================================================================*/
static void swap_fpu_state(struct proc *a_rp, struct proc *b_orig_rp,
struct proc *b_copy_rp)
{
/* Copy the FPU state from process B's copied slot, using B's original FPU
* save area alignment, into process A's slot.
*/
#if (_MINIX_CHIP == _CHIP_INTEL)
int align;
align = (int) ((char *) b_orig_rp->p_fpu_state.fpu_save_area_p -
(char *) &b_orig_rp->p_fpu_state.fpu_image);
memcpy(a_rp->p_fpu_state.fpu_save_area_p,
b_copy_rp->p_fpu_state.fpu_image + align, FPU_XFP_SIZE);
#endif
}
/*===========================================================================*
* swap_proc_slot_pointer *
*===========================================================================*/