コード例 #1
0
/**
  This routine returns the current interrupt status and/or the transmitted buffer addresses.
  If the current interrupt status is returned, pending interrupts will be acknowledged by this
  command.  Transmitted buffer addresses that are written to the DB are removed from the transmit
  buffer queue.
  Normally, this command would be polled with interrupts disabled.
  The transmit buffers are returned in CdbPtr->DBaddr->TxBufer[0 - NumEntries].
  The interrupt status is returned in CdbPtr->StatFlags.

  @param  CdbPtr               Pointer to the command descriptor block.
  @param  AdapterInfo          Pointer to the NIC data structure information which
                               the UNDI driver is layering on..

  @return None

**/
VOID
UNDI_Status (
  IN  PXE_CDB           *CdbPtr,
  IN  NIC_DATA_INSTANCE *AdapterInfo
  )
{
  PXE_DB_GET_STATUS *DbPtr;
  PXE_DB_GET_STATUS TmpGetStatus;
  UINT16            Index;
  UINT16            Status;
  UINT16            NumEntries;
  RxFD              *RxPtr;

  //
  // Fill in temporary GetStatus storage.
  //
  RxPtr = &AdapterInfo->rx_ring[AdapterInfo->cur_rx_ind];

  if ((RxPtr->cb_header.status & RX_COMPLETE) != 0) {
    TmpGetStatus.RxFrameLen = RxPtr->ActualCount & 0x3fff;
  } else {
    TmpGetStatus.RxFrameLen = 0;
  }

  TmpGetStatus.reserved = 0;

  //
  // Fill in size of next available receive packet and
  // reserved field in caller's DB storage.
  //
  DbPtr = (PXE_DB_GET_STATUS *) (UINTN) CdbPtr->DBaddr;

  if (CdbPtr->DBsize > 0 && CdbPtr->DBsize < sizeof (UINT32) * 2) {
    CopyMem (DbPtr, &TmpGetStatus, CdbPtr->DBsize);
  } else {
    CopyMem (DbPtr, &TmpGetStatus, sizeof (UINT32) * 2);
  }

  //
  //
  //
  if ((CdbPtr->OpFlags & PXE_OPFLAGS_GET_TRANSMITTED_BUFFERS) != 0) {
    //
    // DBsize of zero is invalid if Tx buffers are requested.
    //
    if (CdbPtr->DBsize == 0) {
      CdbPtr->StatFlags = PXE_STATFLAGS_COMMAND_FAILED;
      CdbPtr->StatCode  = PXE_STATCODE_INVALID_CDB;
      return ;
    }

    //
    // remember this b4 we overwrite
    //
    NumEntries = (UINT16) (CdbPtr->DBsize - sizeof (UINT64));

    //
    // We already filled in 2 UINT32s.
    //
    CdbPtr->DBsize = sizeof (UINT32) * 2;

    //
    // will claim any hanging free CBs
    //
    CheckCBList (AdapterInfo);

    if (AdapterInfo->xmit_done_head == AdapterInfo->xmit_done_tail) {
      CdbPtr->StatFlags |= PXE_STATFLAGS_GET_STATUS_TXBUF_QUEUE_EMPTY;
    } else {
      for (Index = 0; NumEntries >= sizeof (UINT64); Index++, NumEntries -= sizeof (UINT64)) {
        if (AdapterInfo->xmit_done_head != AdapterInfo->xmit_done_tail) {
          DbPtr->TxBuffer[Index]      = AdapterInfo->xmit_done[AdapterInfo->xmit_done_head];
          AdapterInfo->xmit_done_head = next (AdapterInfo->xmit_done_head);
          CdbPtr->DBsize += sizeof (UINT64);
        } else {
          break;
        }
      }
    }

    if (AdapterInfo->xmit_done_head != AdapterInfo->xmit_done_tail) {
      CdbPtr->StatFlags |= PXE_STATFLAGS_DB_WRITE_TRUNCATED;

    }
    //
    // check for a receive buffer and give it's size in db
    //
  }
  //
  //
  //
  if ((CdbPtr->OpFlags & PXE_OPFLAGS_GET_INTERRUPT_STATUS) != 0) {

    Status = InWord (AdapterInfo, AdapterInfo->ioaddr + SCBStatus);
    AdapterInfo->Int_Status = (UINT16) (AdapterInfo->Int_Status | Status);

    //
    // acknoledge the interrupts
    //
    OutWord (AdapterInfo, (UINT16) (Status & 0xfc00), (UINT32) (AdapterInfo->ioaddr + SCBStatus));

    //
    // report all the outstanding interrupts
    //
    Status = AdapterInfo->Int_Status;
    if ((Status & SCB_STATUS_FR) != 0) {
      CdbPtr->StatFlags |= PXE_STATFLAGS_GET_STATUS_RECEIVE;
    }

    if ((Status & SCB_STATUS_SWI) != 0) {
      CdbPtr->StatFlags |= PXE_STATFLAGS_GET_STATUS_SOFTWARE;
    }
  }

  //
  // Return current media status
  //
  if ((CdbPtr->OpFlags & PXE_OPFLAGS_GET_MEDIA_STATUS) != 0) {
    AdapterInfo->PhyAddress = 0xFF;
    AdapterInfo->CableDetect = 1;

    if (!PhyDetect (AdapterInfo)) {
      CdbPtr->StatFlags |= PXE_STATFLAGS_GET_STATUS_NO_MEDIA;
    }
  }

  return ;
}
コード例 #2
0
ファイル: v86.c プロジェクト: cod5/kielder
int V86HandleOpcode (struct ContextState *state)
{
	bool is_operand32 = FALSE;
	bool is_address32 = FALSE;
	uint32 *sp32;
	uint16 *sp16;
	uint32 eflags;
	uint8 *ip;
		
	uint32 new_ip;
	uint32 new_cs;
	uint8 *vector;

	
	
	
	while (1)
	{
		ip = V86GetAddress (state->return_eip, state->return_cs);
		
		switch (*ip)
		{
			case PREFIX_O32:
				is_operand32 = TRUE;
				state->return_eip = (state->return_eip + 1) & 0x0000ffff;
				continue;
				
			case PREFIX_A32:
				is_address32 = TRUE;
				ip++;
				state->return_eip = (state->return_eip + 1) & 0x0000ffff;
				continue;
			
				
			case OPCODE_PUSHF:
				if (is_operand32 == TRUE)
				{
					state->return_esp = ((state->return_esp & 0x0000ffff) - 4) & 0x0000ffff;
					sp32 = V86GetAddress (state->return_esp, state->return_ss);
					eflags = state->return_eflags & V86_EFLAG_MASK;

					*sp32 = (v86_if == TRUE)
							? eflags | EFLAG_IF
							: eflags & ~EFLAG_IF;
				}
				else
				{
					state->return_esp = ((state->return_esp & 0x0000ffff) - 2) & 0x0000ffff; 
					sp16 = V86GetAddress (state->return_esp, state->return_ss);
					eflags = state->return_eflags & V86_EFLAG_MASK;

					*sp16 = (uint16) (v86_if == TRUE)
							? eflags | EFLAG_IF
							: eflags & ~EFLAG_IF;					
					
				}
			
				state->return_eip = (state->return_eip + 1) & 0x0000ffff;
				return 0;
				
			case OPCODE_POPF:
				if (is_operand32 == TRUE)
				{
					sp32 = V86GetAddress (state->return_esp, state->return_ss);
					eflags = *sp32;
					state->return_eflags = (eflags & V86_EFLAG_MASK) | EFLAG_IF | EFLAG_VM;
					v86_if = (eflags & EFLAG_IF) ? TRUE : FALSE;
					state->return_esp = ((state->return_esp & 0x0000ffff) + 4) & 0x0000ffff;
				}
				else
				{
					sp16 = V86GetAddress (state->return_esp, state->return_ss);
					eflags = *sp16;
					state->return_eflags = (eflags & V86_EFLAG_MASK) | EFLAG_IF | EFLAG_VM;
					v86_if = (eflags & EFLAG_IF) ? TRUE : FALSE;
					state->return_esp = ((state->return_esp & 0x0000ffff) + 2) & 0x0000ffff;
				}

				state->return_eip = (state->return_eip + 1) & 0x0000ffff;
				return 0;

			
			case OPCODE_INT:
			{
				state->return_eip = (state->return_eip + 1) & 0x0000ffff;
				vector = V86GetAddress (state->return_eip, state->return_cs);
				V86GetInterruptVector (*vector, &new_ip, &new_cs);
				state->return_eip = (state->return_eip + 1) & 0x0000ffff;
				
				state->return_esp = ((state->return_esp & 0x0000ffff) - 2) & 0x0000ffff;
				sp16 = V86GetAddress (state->return_esp, state->return_ss);
				*sp16 = (uint16) state->return_eip;
				
				state->return_esp = ((state->return_esp & 0x0000ffff) - 2) & 0x0000ffff;
				sp16 = V86GetAddress (state->return_esp, state->return_ss);
				*sp16 = (uint16) state->return_cs;
				
				state->return_esp = ((state->return_esp & 0x0000ffff) - 2) & 0x0000ffff;
				sp16 = V86GetAddress (state->return_esp, state->return_ss);
				
				eflags = (v86_if == TRUE)
						? (state->return_eflags & V86_EFLAG_MASK) | EFLAG_IF
						: (state->return_eflags & V86_EFLAG_MASK) & ~EFLAG_IF;
				
				*sp16 = (uint16) eflags;
				
				state->return_eflags = (state->return_eflags & ~(EFLAG_IF | EFLAG_TF | EFLAG_AC)) | EFLAG_VM;
				v86_if = FALSE;
				
				state->return_eip = new_ip & 0x0000ffff;
				state->return_cs = new_cs & 0x0000ffff;
				
				return 0;
			}
			
			case OPCODE_IRET:
				if (state->return_eip == 0x0002 && state->return_cs == 0x1000)
				{
					return 1;
				}
				else
				{
					sp16 = V86GetAddress (state->return_esp, state->return_ss);
					eflags = *sp16;
					
					eflags = (eflags & 0x257fd5) | (state->return_eflags & 0x1a0000);
					
					state->return_eflags = eflags | EFLAG_IF | EFLAG_VM;
					v86_if = (eflags & EFLAG_IF) ? TRUE : FALSE;
							
					state->return_esp = ((state->return_esp & 0x0000ffff) + 2) & 0x0000ffff;
					
					sp16 = V86GetAddress (state->return_esp, state->return_ss);
					state->return_cs = *sp16;
					state->return_esp = ((state->return_esp & 0x0000ffff) + 2) & 0x0000ffff;
					
					sp16 = V86GetAddress (state->return_esp, state->return_ss);
					state->return_eip = *sp16;
					state->return_esp = ((state->return_esp & 0x0000ffff) + 2) & 0x0000ffff;

					return 0;
				}
							
				
			case OPCODE_CLI:
				v86_if = FALSE;
				state->return_eip = (state->return_eip + 1) & 0x0000ffff;
				return 0;
							
			case OPCODE_STI:
				v86_if = TRUE;
				state->return_eip = (state->return_eip + 1) & 0x0000ffff;
				return 0;
					
		
			case OPCODE_OUTB:
				OutByte (state->edx, state->eax);
				state->return_eip = (state->return_eip + 1) & 0x0000ffff;
				return 0;
			
			case OPCODE_INB:
				state->eax = InByte (state->edx);
				state->return_eip = (state->return_eip + 1) & 0x0000ffff;
				return 0;
			
			case OPCODE_OUTWL:
				if(is_operand32 == FALSE)
					OutWord (state->edx, state->eax);
				else
					OutLong (state->edx, state->eax);
				
				state->return_eip = (state->return_eip + 1) & 0x0000ffff;
				return 0;
			
			case OPCODE_INWL:
				if(is_operand32 == FALSE)
					state->eax = InWord (state->edx);
				else
					state->eax = InLong (state->edx);

				state->return_eip = (state->return_eip + 1) & 0x0000ffff;
				return 0;

			case OPCODE_OUTB_AL_NN:
				OutByte (*(ip+1), state->eax);
				state->return_eip = (state->return_eip + 2) & 0x0000ffff;
				return 0;

			case OPCODE_INB_NN_AL:
				state->eax = InByte (*(ip+1));
				state->return_eip = (state->return_eip + 2) & 0x0000ffff;
				return 0;
			
			case OPCODE_OUTWL_EAX_NN:
				if (is_operand32 == FALSE)
					OutWord (*(ip+1), state->eax);
				else
					OutLong (*(ip+1), state->eax);

				state->return_eip = (state->return_eip + 2) & 0x0000ffff;
				return 0;
			
			case OPCODE_INWL_NN_EAX:
				if(is_operand32 == FALSE)
					state->eax = InWord (*(ip+1));
				else
					state->eax = InLong (*(ip+1));
				
				state->return_eip = (state->return_eip + 2) & 0x0000ffff;
				return 0;
			
			
			case OPCODE_HLT:
			{
				KPANIC ("Halt in V86");
			}
			
			default:
			{
				KPRINTF ("opcode = %#010x", *ip);
				KPANIC ("#GP Unknown V86 opcode");
			}
		}
	}
}
コード例 #3
0
ファイル: TextStrSo.c プロジェクト: att/uwin
static XmTextPosition
Scan(XmTextSource source, XmTextPosition pos, XmTextScanType type,
     XmTextScanDirection dir, int count, Boolean inc)
{
    XmSourceData d = source->data;
    Boolean found = False;
    char *ptr;
#ifdef VERBOSE__LtDebug
    XmTextPosition ipos = pos;
#endif

    if (pos > d->length)
    {
#if 0
	/* This is reported to be a bad idea. */
	pos = d->length;
#endif
	return(pos);
    }

    if (count < 0)
    {
	count = d->length;
    }

    /*
     * This may not be completely right.
     *      If you start in whitespace, move towards non-whitespace before
     *      doing anything else.
     *      Currently, do this for XmSELECT_WORD.
     *      It may be appropriate to do this for other selections as well.
     * Danny 4/6/97
     */
    if (dir == XmsdLeft && type == XmSELECT_WORD)
    {
	ptr = StrPtr(d, pos - 1);
	while (count > 0 && pos > 0 && InWhiteSpace(*ptr))
	{
	    pos--;
	    ptr = StrPtr(d, pos - 1);
	}
    }
    else if (dir == XmsdRight && type == XmSELECT_WORD)
    {
	ptr = StrPtr(d, pos);
	while (count > 0 && pos < d->length && InWhiteSpace(*ptr))
	{
	    pos++;
	    ptr = StrPtr(d, pos);
	}
    }

    /* End initial whitespace treatment */

    if (dir == XmsdLeft)
    {
	while (count > 0 && pos > 0)
	{
	    ptr = StrPtr(d, pos - 1);
	    switch (type)
	    {
	    case XmSELECT_WHITESPACE:
		if (!InWhiteSpace(*ptr))
		{
		    found = True;
		}
		break;

	    case XmSELECT_WORD:
		if (!InWord(*ptr))
		{
		    found = True;
		}
		break;

	    case XmSELECT_LINE:
		if (*ptr == '\n')
		{
		    found = True;
		}
		break;

	    case XmSELECT_PARAGRAPH:
		if (*ptr == '\n')
		{
		    found = True;
		}
		break;

	    case XmSELECT_ALL:
		/*CP: probably a bit too simple */
		found = True;
		pos = 0;
		break;

	    default:
		found = True;
		break;
	    }

	    if (found)
	    {
#ifdef VERBOSE__LtDebug
		DEBUGOUT(_LtDebug(__FILE__, (Widget)d->widgets[0],
				  "Scan(%d)=>%d\n", ipos, pos));
#endif
		count--;
		if ( count == 0 )
		    return ( inc ? pos - 1 : pos );
		found = False;    
	    }

	    pos--;
	}
    }
    else
    {				/* dir == XmsdRight */
	while (count > 0 && pos < d->length)
	{
	    ptr = StrPtr(d, pos);
	    switch (type)
	    {
	    case XmSELECT_WHITESPACE:
		if (!InWhiteSpace(*ptr))
		{
		    found = True;
		}
		break;

	    case XmSELECT_WORD:
		if (!InWord(*ptr))
		{
		    found = True;
		}
		break;

	    case XmSELECT_LINE:
		if (*ptr == '\n')
		{
		    found = True;
		}
		break;

	    case XmSELECT_PARAGRAPH:
		if (*ptr == '\n')
		{
		    found = True;
		}
		break;

	    case XmSELECT_ALL:
		if (! *ptr )
		{
		    found = True;
		}
		break;

	    default:
		found = True;
		break;
	    }

	    if (found)
	    {
#ifdef VERBOSE__LtDebug
		DEBUGOUT(_LtDebug(__FILE__, (Widget)d->widgets[0],
				  "Scan(%d)=>%d\n", ipos, pos));
#endif
		count--;
		if ( count == 0 )
		    return ( inc ? pos+1 : pos );
		found = False;    
		if ( type == XmSELECT_WORD )
		    while ( InWhiteSpace(*ptr ) )
			{
			pos++;
			ptr = StrPtr(d, pos);
			}
	    }

	    pos++;
	}
    }

#ifdef VERBOSE__LtDebug
    DEBUGOUT(_LtDebug(__FILE__, (Widget)d->widgets[0],
		      "Scan(%d)=>%d\n", ipos, pos));
#endif
    if ( dir == XmsdRight && pos != d->length )
	return ( inc ? pos+1 : pos );
    if ( dir == XmsdLeft && pos != 0 )
	return ( inc ? pos - 1 : pos );
    return pos;
}