Пример #1
0
static
void recursiveReplicate(const EncryptedArray& ea, const Ctxt& ctxt, 
                        long n, long k, long pos, long limit,  
                        RepAux& repAux,
                        ReplicateHandler *handler)
{
  if (pos >= limit) return;

  if (replicateVerboseFlag) {
    // DEBUG code
    cerr << "check: " << k; CheckCtxt(ctxt, "");
  }

  long nSlots = ea.size();

  if (k == 0) {

    if ( (1L << n) >= nSlots) {
      handler->handle(ctxt);
      return;
    }

    // need to replicate to fill positions [ (1L << n) .. nSlots )
    if (repAux.tab(0).null()) {
      // need to generate mask
      ZZX mask;
      SelectRange(ea, mask, 0, nSlots - (1L << n));
      repAux.tab(0).set_ptr(new DoubleCRT(mask, ea.getContext()));
    }


    Ctxt ctxt_tmp = ctxt;
    ctxt_tmp.multByConstant(*repAux.tab(0));

    ea.rotate(ctxt_tmp, 1L << n);
    ctxt_tmp += ctxt;
    handler->handle(ctxt_tmp);
    return;
  }


  k--;

  Ctxt ctxt_masked = ctxt;

  { // artificial scope to miminize storage in
    // the recursion


    { // another artificial scope

      // mask should be at index k+1

      if (repAux.tab(k+1).null()) {
        // need to generate mask

        vector< long > maskArray;
        maskArray.resize(nSlots);
        for (long i = 0; i < (1L << n); i++)
          maskArray[i] = 1- bit(i, k); // the reverse of bit k of i
        for (long i = (1L << n); i < nSlots; i++)
          maskArray[i] = 0;

        ZZX mask;
        ea.encode(mask, maskArray);
        repAux.tab(k+1).set_ptr(new DoubleCRT(mask, ea.getContext()));
      }

      ctxt_masked.multByConstant(*repAux.tab(k+1));
    }

    Ctxt ctxt_left = ctxt_masked;
    ea.rotate(ctxt_left, 1L << k);
    ctxt_left += ctxt_masked;

    recursiveReplicate(ea, ctxt_left, n, k, pos, limit, repAux, handler);
  
  }
 
  pos += (1L << k);
  if (pos >= limit)
    return;

  Ctxt ctxt_right = ctxt;
  ctxt_right -= ctxt_masked; 
  ctxt_masked = ctxt_right; // reuse ctxt_masked as a temp
  ea.rotate(ctxt_masked, -(1L << k));
  ctxt_right += ctxt_masked;

  recursiveReplicate(ea, ctxt_right, n, k, pos, limit, repAux, handler);
}
Пример #2
0
		bit operator [](size_t index)
		{
			return bit(_data, index);
		};
Пример #3
0
int main()
{
   RR::SetPrecision(150);
   long n, b, size;

   cerr << "n: ";
   cin >> n;

   cerr << "b: ";
   cin >> b;

   cerr << "size: ";
   cin >> size;

   cerr << "prune: ";
   long prune;
   cin >> prune;

   ZZ seed;
   cerr << "seed: ";
   cin >> seed;

   if (seed != 0)
      SetSeed(seed);

   char alg;
   cerr << "alg [fqQxr]: ";
   cin >> alg;

   double TotalTime = 0;
   long TotalSucc = 0;

   long iter;

   for (iter = 1; iter <= 20; iter++) {
      vec_ZZ a;
      a.SetLength(n);
   
      ZZ bound;
   
      LeftShift(bound, to_ZZ(1), b);
   
      long i;
      for (i = 1; i <= n; i++) {
         RandomBnd(a(i), bound);
         a(i) += 1;
      }
   
      ZZ S;
   
      do {
         RandomLen(S, n+1);
      } while (weight(S) != n/2+1);
   
      ZZ s;
      clear(s);
      for (i = 1; i <= n; i++)
         if (bit(S, i-1))
            s += a(i);
   
      mat_ZZ B(INIT_SIZE, n+1, n+3);
   
      for (i = 1; i <= n; i++) {
         B(i, i) = 2;
         B(i, n+1) = a(i) * n;
         B(i, n+3) = n;
      }
   
      for (i = 1; i <= n; i++)
         B(n+1, i) = 1;
   
      B(n+1, n+1) = s * n;
      B(n+1, n+2) = 1;
      B(n+1, n+3) = n;
      B(n+1, n+3) *= n/2;
   
      swap(B(1), B(n+1)); 
   
      for (i = 2; i <= n; i++) {
         long j = RandomBnd(n-i+2) + i;
         swap(B(i), B(j));
      }
   
      double t;

      LLLStatusInterval = 10;
   
      t = GetTime();
      switch (alg) {
      case 'f':
         BKZ_FP(B, 0.99, size, prune, SubsetSumSolution);
         break;
      case 'q':
         BKZ_QP(B, 0.99, size, prune, SubsetSumSolution);
         break;
      case 'Q':
         BKZ_QP1(B, 0.99, size, prune, SubsetSumSolution);
         break;
      case 'x':
         BKZ_XD(B, 0.99, size, prune, SubsetSumSolution);
         break;
      case 'r':
         BKZ_RR(B, 0.99, size, prune, SubsetSumSolution);
         break;
      default:
         Error("invalid algorithm");
      }


      t = GetTime()-t;
   
      long succ = 0;
      for (i = 1; i <= n+1; i++)
         if (SubsetSumSolution(B(i)))
            succ = 1;

      TotalTime += t;
      TotalSucc += succ;

      if (succ)
         cerr << "+";
      else
         cerr << "-";
   }

   cerr << "\n";

   cerr << "number of success: " << TotalSucc << "\n";
   cerr << "average time: " << TotalTime/20 << "\n";

   return 0;
}
Пример #4
0
NDIS_STATUS
xmpSetInformation(
  IN xmpNicCtx_t             *pNicCtx,
  IN PNDIS_OID_REQUEST       NdisRequest
  )
{
  NDIS_STATUS                 Status = NDIS_STATUS_SUCCESS;
  NDIS_OID                    Oid;
  PVOID                       InformationBuffer;
  ULONG                       InformationBufferLength;
  ULONG                       BytesRead;
  ULONG                       BytesNeeded;
  ULONG                       PacketFilter;
  ULONG                       MCastCnt;
  ULONG                       HashType;
  ULONG                       validBits;
  USHORT                      i;
  xge_hal_device_t           *pHalDev;
  NDIS_RECEIVE_SCALE_PARAMETERS *pRssParam;
  xmpSetRssContext			      SetRssCtx = {0};
  static ULONG setRssCount = 10;

  pHalDev = XMP_NIC_GET_DEV(pNicCtx);
  Oid = NdisRequest->DATA.SET_INFORMATION.Oid;
  InformationBuffer = NdisRequest->DATA.SET_INFORMATION.InformationBuffer;
  InformationBufferLength = 
    NdisRequest->DATA.SET_INFORMATION.InformationBufferLength;

  XMPTRACE(XMP_DBG_REQ, ("==> xmpSetInformation %x\n", Oid));
  BytesRead = 0;
  BytesNeeded = 0;

  switch(Oid)
  {
  case OID_802_3_MULTICAST_LIST:
    XMPTRACE(XMP_DBG_REQ, ("xmpSetInformation Multicast list\n"));
    if ( InformationBufferLength % ETH_LENGTH_OF_ADDRESS != 0 )
      return(NDIS_STATUS_INVALID_LENGTH);

    MCastCnt = InformationBufferLength / ETH_LENGTH_OF_ADDRESS;
    xmpHalMcastFilterClr(pNicCtx);
    Status = xmpHalSetMcastList(pNicCtx,
                                (UCHAR *) InformationBuffer,
                                &MCastCnt);
    BytesRead = MCastCnt * ETH_LENGTH_OF_ADDRESS;
    break;

  case OID_GEN_CURRENT_PACKET_FILTER:
    XMPTRACE(XMP_DBG_REQ, ("xmpSetInformation: packet filter\n"));
    if ( InformationBufferLength != sizeof (ULONG) )
      return ( NDIS_STATUS_INVALID_LENGTH );

    BytesRead = InformationBufferLength;
    PacketFilter = *((PULONG) InformationBuffer);
    Status = xmpSetFilter(pNicCtx, PacketFilter);
    break;

  case OID_GEN_CURRENT_LOOKAHEAD:
    XMPTRACE(XMP_DBG_REQ, ("xmpSetInformation: current lookahead\n"));
    if( InformationBufferLength < sizeof(ULONG) )
    {
      BytesNeeded = sizeof(ULONG);
      Status = NDIS_STATUS_INVALID_LENGTH;
      break;
    }
    pNicCtx->LookAheadSz = *((PULONG) InformationBuffer);
    BytesRead = sizeof(ULONG);
    Status = NDIS_STATUS_SUCCESS;
    break;

  case OID_GEN_RECEIVE_SCALE_PARAMETERS:

    XMPTRACE(XMP_DBG_INFO, ("xmpSetInformation: OID_GEN_RECEIVE_SCALE_PARAMETERS\n"));
    if ( !(XMP_NIC_RSS_IN_CONFIG(pNicCtx)) )
    {
      Status = NDIS_STATUS_NOT_SUPPORTED;
      break;
    }

    if ( InformationBufferLength < sizeof(NDIS_RECEIVE_SCALE_PARAMETERS) )
    {
      BytesNeeded = sizeof(NDIS_RECEIVE_SCALE_PARAMETERS);
      Status = NDIS_STATUS_INVALID_LENGTH;
      break;
    }
    pRssParam = (PNDIS_RECEIVE_SCALE_PARAMETERS)InformationBuffer;

#ifdef NDISTEST_BUG
    if ( !XENAMP_NDIS_OBJECT_VALID(&pRssParam->Header,
                                   NDIS_RECEIVE_SCALE_PARAMETERS_REVISION_1,
                                   NDIS_OBJECT_TYPE_RSS_PARAMETERS,
                                   sizeof(NDIS_RECEIVE_SCALE_PARAMETERS)) )
    {
      XMPTRACE(XMP_DBG_WRN, ("xmpSetInformation:RSS_PARAMETERS invalid!!"       
                             " Revision=%d Type=%d Size=%d\n",
                             pRssParam->Header.Revision,
                             pRssParam->Header.Type,
                             pRssParam->Header.Size));
      BytesRead = sizeof(NDIS_OBJECT_HEADER);
      Status = NDIS_STATUS_INVALID_PARAMETER;
      break;
    }
#endif

    BytesRead = sizeof(NDIS_RECEIVE_SCALE_PARAMETERS);

    if ( (InformationBufferLength < (pRssParam->IndirectionTableSize
                                     + pRssParam->IndirectionTableOffset)) ||
         (InformationBufferLength < (pRssParam->HashSecretKeySize
                                     + pRssParam->HashSecretKeyOffset)) )
    {
      BytesNeeded = sizeof(NDIS_RECEIVE_SCALE_PARAMETERS);
      Status = NDIS_STATUS_INVALID_LENGTH;
      break;
    }

    HashType = NDIS_RSS_HASH_TYPE_FROM_HASH_INFO(pRssParam->HashInformation);   
    /*if ( HashType != 0 || NDIS_RSS_HASH_FUNC_FROM_HASH_INFO(pRssParam->HashInformation) != 0) */
    validBits = (NDIS_HASH_IPV4 | NDIS_HASH_TCP_IPV4
#ifndef XMP_RSS_IPV4_ONLY
                 | NDIS_HASH_IPV6 | NDIS_HASH_TCP_IPV6
                 | NDIS_HASH_IPV6_EX | NDIS_HASH_TCP_IPV6_EX
#endif
                 );
    if ( ((NDIS_RSS_HASH_FUNC_FROM_HASH_INFO(pRssParam->HashInformation) !=
           NdisHashFunctionToeplitz) ||  /* the only hash function supported */
          !bit(HashType, validBits) ||    /* at least one type should be set */
          (HashType & ~validBits)) &&         /* no other type should be set */
         (!(bit(pRssParam->Flags, NDIS_RSS_PARAM_FLAG_DISABLE_RSS)) &&
          NDIS_RSS_HASH_FUNC_FROM_HASH_INFO(pRssParam->HashInformation) != 0) )
    {
      Status = NDIS_STATUS_INVALID_PARAMETER;
      break;
    }

    if ( /*(pRssParam->IndirectionTableSize < (1 << pRssParam->NumberOfLsbs)) || */
         (pRssParam->HashSecretKeySize & 0x7) ||    /* must be 8-bytes align */
         (pRssParam->HashSecretKeySize > 40)  ||      /* max secret key size */
         (pRssParam->BaseCpuNumber & (pRssParam->BaseCpuNumber - 1)) )/*pow2 */
    {
      XMPTRACE(XMP_DBG_WRN, ("xmpReqSetRss:Invalid settings: Key Size=%d"
                             " IDT size=%d BaseCpu=%d\n",
                             pRssParam->HashSecretKeySize,
                             pRssParam->IndirectionTableSize,
                             pRssParam->BaseCpuNumber));
      Status = NDIS_STATUS_INVALID_PARAMETER;
      break;
    }


    if ((pRssParam->IndirectionTableSize + pRssParam->IndirectionTableOffset) >
        (pRssParam->HashSecretKeySize + pRssParam->HashSecretKeyOffset))
      BytesRead = (pRssParam->IndirectionTableSize + 
                    pRssParam->IndirectionTableOffset);
    else
      BytesRead = (pRssParam->HashSecretKeySize +
                    pRssParam->HashSecretKeyOffset);

    SetRssCtx.pNicCtx = pNicCtx;
    SetRssCtx.pParams = pRssParam;

#if 0
    if(NdisMSynchronizeWithInterruptEx(pNicCtx->hInterrupt, 0, xmpReqSetRss, &SetRssCtx))
#endif
    if ( NDIS_RSS_HASH_FUNC_FROM_HASH_INFO(pRssParam->HashInformation) == 0 )
      bis(pRssParam->Flags, NDIS_RSS_PARAM_FLAG_DISABLE_RSS);

    if ( bit(pRssParam->Flags, NDIS_RSS_PARAM_FLAG_DISABLE_RSS) )
    {
      pNicCtx->ndisRssSet.size = sizeof(NDIS_RECEIVE_SCALE_PARAMETERS);
      pNicCtx->ndisRssSet.params.BaseCpuNumber          = 0;
      pNicCtx->ndisRssSet.params.Flags                  = 0;
      pNicCtx->ndisRssSet.params.HashInformation        = 0;
      pNicCtx->ndisRssSet.params.IndirectionTableSize   = 0;
      pNicCtx->ndisRssSet.params.IndirectionTableOffset = 0;
      pNicCtx->ndisRssSet.params.HashSecretKeySize      = 0;
      pNicCtx->ndisRssSet.params.HashSecretKeyOffset    = 0;
    }
    else
    {
      NdisMoveMemory(&pNicCtx->ndisRssSet.params, pRssParam, BytesRead);
      pNicCtx->ndisRssSet.size = BytesRead;
    }

      xmpReqSetRss(pNicCtx);
#if 0
    if ( !(setRssCount % 10) )
    {
      xmpReqSetRss(pNicCtx);
    }
    setRssCount++;
#endif
    Status = NDIS_STATUS_SUCCESS;
    break;

  case OID_OFFLOAD_ENCAPSULATION:
    XMPTRACE(XMP_DBG_OFLD, ("xmpSetInformation: offload encapsulation\n"));
    if ( InformationBufferLength < sizeof(NDIS_OFFLOAD_ENCAPSULATION) )
    {
      BytesNeeded = sizeof(NDIS_OFFLOAD_ENCAPSULATION);
      Status = NDIS_STATUS_INVALID_LENGTH;
      break;
    }

    NdisMoveMemory(&pNicCtx->OffloadEncapsulation,
                   InformationBuffer,
                   sizeof(NDIS_OFFLOAD_ENCAPSULATION));
    BytesRead = sizeof(NDIS_OFFLOAD_ENCAPSULATION);
    Status    = NDIS_STATUS_SUCCESS;
    break;

  case OID_GEN_INTERRUPT_MODERATION:
    {
      NDIS_INTERRUPT_MODERATION_PARAMETERS *pIntrModr;
      if ( InformationBufferLength < sizeof(NDIS_INTERRUPT_MODERATION_PARAMETERS) )
      {
        BytesNeeded = sizeof(NDIS_INTERRUPT_MODERATION_PARAMETERS);
        Status = NDIS_STATUS_INVALID_LENGTH;
        break;
      }
      pIntrModr  = (NDIS_INTERRUPT_MODERATION_PARAMETERS *) InformationBuffer;
      if ( !XENAMP_NDIS_OBJECT_VALID(&pIntrModr->Header,
                                 NDIS_INTERRUPT_MODERATION_PARAMETERS_REVISION_1,
                                 NDIS_OBJECT_TYPE_DEFAULT,
                                 sizeof(NDIS_INTERRUPT_MODERATION_PARAMETERS)) )
      {
        BytesRead = sizeof(NDIS_OBJECT_HEADER);
        Status = NDIS_STATUS_INVALID_DATA;
        break;
      }
     break;
    }

  case OID_TCP_OFFLOAD_PARAMETERS:
    {
      NDIS_OFFLOAD_PARAMETERS *pAdmin;
      NDIS_STATUS_INDICATION  StatusIndication;
      ULONG size;

      pAdmin  = (NDIS_OFFLOAD_PARAMETERS *) InformationBuffer;
  
      if ( InformationBufferLength < NDIS_SIZEOF_OFFLOAD_PARAMETERS_REVISION_1 )
      {
        BytesNeeded = NDIS_SIZEOF_OFFLOAD_PARAMETERS_REVISION_1;
        Status = NDIS_STATUS_INVALID_LENGTH;
        break;
      }

      if ( !XENAMP_NDIS_OBJECT_VALID(&pAdmin->Header,
                                     NDIS_OFFLOAD_PARAMETERS_REVISION_1,
                                     NDIS_OBJECT_TYPE_DEFAULT,
                                     NDIS_SIZEOF_OFFLOAD_PARAMETERS_REVISION_1 ))
      {
        BytesRead = sizeof(NDIS_OBJECT_HEADER);
        Status = NDIS_STATUS_INVALID_DATA;
        break;
      }

      XMP_NIC_SET_ADMIN_OFFLOADS(pNicCtx, pAdmin);
      xmpNicSetCkoFlags(pNicCtx);
      xmpNicInitOffloadCapabilities(pNicCtx, &pNicCtx->OffloadCapabilities);    
       /* TODO: Generate event */
      BytesRead = NDIS_SIZEOF_OFFLOAD_PARAMETERS_REVISION_1;
      Status    = NDIS_STATUS_SUCCESS;

      XENAMP_NDIS_OBJECT_INIT(&StatusIndication.Header,
         NDIS_OBJECT_TYPE_STATUS_INDICATION,
         NDIS_STATUS_INDICATION_REVISION_1,
         sizeof(NDIS_STATUS_INDICATION));

      StatusIndication.SourceHandle = pNicCtx->hMPAdapter;
      StatusIndication.PortNumber = 0;
      StatusIndication.StatusCode = NDIS_STATUS_TASK_OFFLOAD_CURRENT_CONFIG;
      StatusIndication.Flags = 0;
      StatusIndication.DestinationHandle = NULL;
      StatusIndication.RequestId = NdisRequest->RequestId;
      StatusIndication.StatusBuffer = &pNicCtx->OffloadCapabilities;
      StatusIndication.StatusBufferSize = sizeof(NDIS_OFFLOAD);
      NdisMIndicateStatusEx(pNicCtx->hMPAdapter, &StatusIndication);
    }
    break;
    
  case OID_GEN_HD_SPLIT_PARAMETERS:
     {
       NDIS_HD_SPLIT_PARAMETERS *pHdSplit;
    
       pHdSplit  = (NDIS_HD_SPLIT_PARAMETERS *) InformationBuffer;
       if ( InformationBufferLength < NDIS_SIZEOF_HD_SPLIT_PARAMETERS_REVISION_1 )
       {
         BytesNeeded = NDIS_SIZEOF_HD_SPLIT_PARAMETERS_REVISION_1;
         Status = NDIS_STATUS_INVALID_LENGTH;
         break;
       }

       if ( !XENAMP_NDIS_OBJECT_VALID(&pHdSplit->Header,
                                    NDIS_HD_SPLIT_PARAMETERS_REVISION_1,
                                    NDIS_OBJECT_TYPE_DEFAULT,                                     
                                    NDIS_SIZEOF_HD_SPLIT_PARAMETERS_REVISION_1 ))
       {
         BytesRead = sizeof(NDIS_OBJECT_HEADER);
         Status = NDIS_STATUS_INVALID_DATA;
         break;
       }
      
       if( bit(pHdSplit->HDSplitCombineFlags, NDIS_HD_SPLIT_COMBINE_ALL_HEADERS) ) 
         bis( pNicCtx->Flags, XMP_NIC_FLAGS_RX_SPLIT_COMBINE ); 
       else
         bic( pNicCtx->Flags, XMP_NIC_FLAGS_RX_SPLIT_COMBINE ); 
    }
    break;

  default:
    XMPTRACE(XMP_DBG_INFO, ("xmpSetInformation: unsupported OID=%lx\n", Oid));
    Status = xmpDiagSetInformation(
                                   pNicCtx, 
                                   Oid, 
                                   InformationBuffer, 
                                   InformationBufferLength,
                                   &BytesRead,
                                   &BytesNeeded);
    break;
  }

  NdisRequest->DATA.SET_INFORMATION.BytesRead = BytesRead;
  NdisRequest->DATA.SET_INFORMATION.BytesNeeded = BytesNeeded;

  XMPTRACE(XMP_DBG_REQ, ("<== xmpSetInformation: Status=%x\n", Status));
  return Status;
}
Пример #5
0
/*
 * Function: byte_set_bits
 * Purpose:
 *   Set the given range of bits within a byte.
 */
static __inline__ u_char
byte_set_bits(int start, int end)
{
    return ((u_char)((~bits_lower(start)) & (bits_lower(end) | bit(end))));
}
Пример #6
0
/*
 * Calculates the FSB and CPU frequencies using specific MSRs for each CPU
 * - multi. is read from a specific MSR. In the case of Intel, there is:
 *	   a max multi. (used to calculate the FSB freq.),
 *	   and a current multi. (used to calculate the CPU freq.)
 * - fsbFrequency = tscFrequency / multi
 * - cpuFrequency = fsbFrequency * multi
 */
void scan_cpu(PlatformInfo_t *p)
{
	uint64_t	tscFrequency, fsbFrequency, cpuFrequency;
	uint64_t	msr, flex_ratio;
	uint8_t		maxcoef, maxdiv, currcoef, bus_ratio_max, currdiv;
	const char	*newratio;
	int			len, myfsb;
	uint8_t		bus_ratio_min;
	uint32_t	max_ratio, min_ratio;
	
	max_ratio = min_ratio = myfsb = bus_ratio_min = 0;
	maxcoef = maxdiv = bus_ratio_max = currcoef = currdiv = 0;
	
	/* get cpuid values */
	do_cpuid(0x00000000, p->CPU.CPUID[CPUID_0]);
	do_cpuid(0x00000001, p->CPU.CPUID[CPUID_1]);
	do_cpuid(0x00000002, p->CPU.CPUID[CPUID_2]);
	do_cpuid(0x00000003, p->CPU.CPUID[CPUID_3]);
	do_cpuid2(0x00000004, 0, p->CPU.CPUID[CPUID_4]);
	do_cpuid(0x80000000, p->CPU.CPUID[CPUID_80]);
	if (p->CPU.CPUID[CPUID_0][0] >= 0x5) {		
		do_cpuid(5,  p->CPU.CPUID[CPUID_5]);        	
	}	
	if (p->CPU.CPUID[CPUID_0][0] >= 6) {
		do_cpuid(6, p->CPU.CPUID[CPUID_6]);		
	}
	if ((p->CPU.CPUID[CPUID_80][0] & 0x0000000f) >= 8) {
		do_cpuid(0x80000008, p->CPU.CPUID[CPUID_88]);
		do_cpuid(0x80000001, p->CPU.CPUID[CPUID_81]);
	}
	else if ((p->CPU.CPUID[CPUID_80][0] & 0x0000000f) >= 1) {
		do_cpuid(0x80000001, p->CPU.CPUID[CPUID_81]);
	}
	
#if DEBUG_CPU
	{
		int		i;
		printf("CPUID Raw Values:\n");
		for (i=0; i<CPUID_MAX; i++) {
			printf("%02d: %08x-%08x-%08x-%08x\n", i,
				   p->CPU.CPUID[i][0], p->CPU.CPUID[i][1],
				   p->CPU.CPUID[i][2], p->CPU.CPUID[i][3]);
		}
	}
#endif
	
	p->CPU.Vendor		= p->CPU.CPUID[CPUID_0][1];
	p->CPU.Signature	= p->CPU.CPUID[CPUID_1][0];
	p->CPU.Stepping		= bitfield(p->CPU.CPUID[CPUID_1][0], 3, 0);
	p->CPU.Model		= bitfield(p->CPU.CPUID[CPUID_1][0], 7, 4);
	p->CPU.Family		= bitfield(p->CPU.CPUID[CPUID_1][0], 11, 8);
	p->CPU.ExtModel		= bitfield(p->CPU.CPUID[CPUID_1][0], 19, 16);
	p->CPU.ExtFamily	= bitfield(p->CPU.CPUID[CPUID_1][0], 27, 20);
	
	p->CPU.Model += (p->CPU.ExtModel << 4);
	
	if (p->CPU.Vendor == CPUID_VENDOR_INTEL &&
		p->CPU.Family == 0x06 &&
		p->CPU.Model >= CPUID_MODEL_NEHALEM &&
		p->CPU.Model != CPUID_MODEL_ATOM		// MSR is *NOT* available on the Intel Atom CPU
		)
	{
		msr = rdmsr64(MSR_CORE_THREAD_COUNT);					// Undocumented MSR in Nehalem and newer CPUs
		p->CPU.NoCores		= bitfield((uint32_t)msr, 31, 16);	// Using undocumented MSR to get actual values
		p->CPU.NoThreads	= bitfield((uint32_t)msr, 15,  0);	// Using undocumented MSR to get actual values
	}
	else if (p->CPU.Vendor == CPUID_VENDOR_AMD)
	{
		p->CPU.NoThreads	= bitfield(p->CPU.CPUID[CPUID_1][1], 23, 16);
		p->CPU.NoCores		= bitfield(p->CPU.CPUID[CPUID_88][2], 7, 0) + 1;
	}
	else
	{
		// Use previous method for Cores and Threads
		p->CPU.NoThreads	= bitfield(p->CPU.CPUID[CPUID_1][1], 23, 16);
		p->CPU.NoCores		= bitfield(p->CPU.CPUID[CPUID_4][0], 31, 26) + 1;
	}
	
	/* get brand string (if supported) */
	/* Copyright: from Apple's XNU cpuid.c */
	if (p->CPU.CPUID[CPUID_80][0] > 0x80000004) {
		uint32_t	reg[4];
		char		str[128], *s;
		/*
		 * The brand string 48 bytes (max), guaranteed to
		 * be NULL terminated.
		 */
		do_cpuid(0x80000002, reg);
		bcopy((char *)reg, &str[0], 16);
		do_cpuid(0x80000003, reg);
		bcopy((char *)reg, &str[16], 16);
		do_cpuid(0x80000004, reg);
		bcopy((char *)reg, &str[32], 16);
		for (s = str; *s != '\0'; s++) {
			if (*s != ' ') break;
		}
		
		strlcpy(p->CPU.BrandString, s, sizeof(p->CPU.BrandString));
		
		if (!strncmp(p->CPU.BrandString, CPU_STRING_UNKNOWN, MIN(sizeof(p->CPU.BrandString), strlen(CPU_STRING_UNKNOWN) + 1))) {
			/*
			 * This string means we have a firmware-programmable brand string,
			 * and the firmware couldn't figure out what sort of CPU we have.
			 */
			p->CPU.BrandString[0] = '\0';
		}
	}
	
	/* setup features */
	if ((bit(23) & p->CPU.CPUID[CPUID_1][3]) != 0) {
		p->CPU.Features |= CPU_FEATURE_MMX;
	}
	if ((bit(25) & p->CPU.CPUID[CPUID_1][3]) != 0) {
		p->CPU.Features |= CPU_FEATURE_SSE;
	}
	if ((bit(26) & p->CPU.CPUID[CPUID_1][3]) != 0) {
		p->CPU.Features |= CPU_FEATURE_SSE2;
	}
	if ((bit(0) & p->CPU.CPUID[CPUID_1][2]) != 0) {
		p->CPU.Features |= CPU_FEATURE_SSE3;
	}
	if ((bit(19) & p->CPU.CPUID[CPUID_1][2]) != 0) {
		p->CPU.Features |= CPU_FEATURE_SSE41;
	}
	if ((bit(20) & p->CPU.CPUID[CPUID_1][2]) != 0) {
		p->CPU.Features |= CPU_FEATURE_SSE42;
	}
	if ((bit(29) & p->CPU.CPUID[CPUID_81][3]) != 0) {
		p->CPU.Features |= CPU_FEATURE_EM64T;
	}
	if ((bit(5) & p->CPU.CPUID[CPUID_1][3]) != 0) {
		p->CPU.Features |= CPU_FEATURE_MSR;
	}
	//if ((bit(28) & p->CPU.CPUID[CPUID_1][3]) != 0) {
	if (p->CPU.NoThreads > p->CPU.NoCores) {
		p->CPU.Features |= CPU_FEATURE_HTT;
	}
	
	tscFrequency = measure_tsc_frequency();
	/* if usual method failed */
	if ( tscFrequency < 1000 )
	{
	tscFrequency = timeRDTSC() * 20;
	}
	fsbFrequency = 0;
	cpuFrequency = 0;
	
	if ((p->CPU.Vendor == CPUID_VENDOR_INTEL) && ((p->CPU.Family == 0x06) || (p->CPU.Family == 0x0f))) {
		int intelCPU = p->CPU.Model;
		if ((p->CPU.Family == 0x06 && p->CPU.Model >= 0x0c) || (p->CPU.Family == 0x0f && p->CPU.Model >= 0x03)) {
			/* Nehalem CPU model */
			if (p->CPU.Family == 0x06 && (p->CPU.Model == CPU_MODEL_NEHALEM ||
										  p->CPU.Model == CPU_MODEL_FIELDS ||
										  p->CPU.Model == CPU_MODEL_DALES ||
										  p->CPU.Model == CPU_MODEL_DALES_32NM ||
										  p->CPU.Model == CPU_MODEL_WESTMERE ||
										  p->CPU.Model == CPU_MODEL_NEHALEM_EX ||
										  p->CPU.Model == CPU_MODEL_WESTMERE_EX ||
										  p->CPU.Model == CPU_MODEL_SANDYBRIDGE ||
										  p->CPU.Model == CPU_MODEL_JAKETOWN ||
										  p->CPU.Model == CPU_MODEL_IVYBRIDGE)) {
				msr = rdmsr64(MSR_PLATFORM_INFO);
				DBG("msr(%d): platform_info %08x\n", __LINE__, bitfield(msr, 31, 0));
				bus_ratio_max = bitfield(msr, 14, 8);
				bus_ratio_min = bitfield(msr, 46, 40); //valv: not sure about this one (Remarq.1)
				msr = rdmsr64(MSR_FLEX_RATIO);
				DBG("msr(%d): flex_ratio %08x\n", __LINE__, bitfield(msr, 31, 0));
				if (bitfield(msr, 16, 16)) {
					flex_ratio = bitfield(msr, 14, 8);
					/* bcc9: at least on the gigabyte h67ma-ud2h,
					 where the cpu multipler can't be changed to
					 allow overclocking, the flex_ratio msr has unexpected (to OSX)
					 contents.	These contents cause mach_kernel to
					 fail to compute the bus ratio correctly, instead
					 causing the system to crash since tscGranularity
					 is inadvertently set to 0.
					 */
					if (flex_ratio == 0) {
						/* Clear bit 16 (evidently the presence bit) */
						wrmsr64(MSR_FLEX_RATIO, (msr & 0xFFFFFFFFFFFEFFFFULL));
						msr = rdmsr64(MSR_FLEX_RATIO);
						verbose("Unusable flex ratio detected. Patched MSR now %08x\n", bitfield(msr, 31, 0));
					} else {
						if (bus_ratio_max > flex_ratio) {
							bus_ratio_max = flex_ratio;
						}
					}
				}
				
				if (bus_ratio_max) {
					fsbFrequency = (tscFrequency / bus_ratio_max);
				}
				//valv: Turbo Ratio Limit
				if ((intelCPU != 0x2e) && (intelCPU != 0x2f)) {
					msr = rdmsr64(MSR_TURBO_RATIO_LIMIT);
					cpuFrequency = bus_ratio_max * fsbFrequency;
					max_ratio = bus_ratio_max * 10;
				} else {
					cpuFrequency = tscFrequency;
				}
				if ((getValueForKey(kbusratio, &newratio, &len, &bootInfo->chameleonConfig)) && (len <= 4)) {
					max_ratio = atoi(newratio);
					max_ratio = (max_ratio * 10);
					if (len >= 3) max_ratio = (max_ratio + 5);
					
					verbose("Bus-Ratio: min=%d, max=%s\n", bus_ratio_min, newratio);
					
					// extreme overclockers may love 320 ;)
					if ((max_ratio >= min_ratio) && (max_ratio <= 320)) {
						cpuFrequency = (fsbFrequency * max_ratio) / 10;
						if (len >= 3) maxdiv = 1;
						else maxdiv = 0;
					} else {
						max_ratio = (bus_ratio_max * 10);
					}
				}
				//valv: to be uncommented if Remarq.1 didn't stick
				/*if (bus_ratio_max > 0) bus_ratio = flex_ratio;*/
				p->CPU.MaxRatio = max_ratio;
				p->CPU.MinRatio = min_ratio;
				
				myfsb = fsbFrequency / 1000000;
				verbose("Sticking with [BCLK: %dMhz, Bus-Ratio: %d]\n", myfsb, max_ratio);
				currcoef = bus_ratio_max;
			} else {
				msr = rdmsr64(MSR_IA32_PERF_STATUS);
				DBG("msr(%d): ia32_perf_stat 0x%08x\n", __LINE__, bitfield(msr, 31, 0));
				currcoef = bitfield(msr, 12, 8);
				/* Non-integer bus ratio for the max-multi*/
				maxdiv = bitfield(msr, 46, 46);
				/* Non-integer bus ratio for the current-multi (undocumented)*/
				currdiv = bitfield(msr, 14, 14);
				
				// This will always be model >= 3
				if ((p->CPU.Family == 0x06 && p->CPU.Model >= 0x0e) || (p->CPU.Family == 0x0f))
				{
					/* On these models, maxcoef defines TSC freq */
					maxcoef = bitfield(msr, 44, 40);
				} else {
					/* On lower models, currcoef defines TSC freq */
					/* XXX */
					maxcoef = currcoef;
				}
				
				if (maxcoef) {
					if (maxdiv) {
						fsbFrequency = ((tscFrequency * 2) / ((maxcoef * 2) + 1));
					} else {
						fsbFrequency = (tscFrequency / maxcoef);
					}
					if (currdiv) {
						cpuFrequency = (fsbFrequency * ((currcoef * 2) + 1) / 2);
					} else {
						cpuFrequency = (fsbFrequency * currcoef);
					}
					DBG("max: %d%s current: %d%s\n", maxcoef, maxdiv ? ".5" : "",currcoef, currdiv ? ".5" : "");
				}
			}
		}
		/* Mobile CPU */
		if (rdmsr64(MSR_IA32_PLATFORM_ID) & (1<<28)) {
			p->CPU.Features |= CPU_FEATURE_MOBILE;
		}
	}
	else if ((p->CPU.Vendor == CPUID_VENDOR_AMD) && (p->CPU.Family == 0x0f))
	{
		switch(p->CPU.ExtFamily)
		{
			case 0x00: /* K8 */
				msr = rdmsr64(K8_FIDVID_STATUS);
				maxcoef = bitfield(msr, 21, 16) / 2 + 4;
				currcoef = bitfield(msr, 5, 0) / 2 + 4;
				break;
				
			case 0x01: /* K10 */
				msr = rdmsr64(K10_COFVID_STATUS);
				do_cpuid2(0x00000006, 0, p->CPU.CPUID[CPUID_6]);
				// EffFreq: effective frequency interface
				if (bitfield(p->CPU.CPUID[CPUID_6][2], 0, 0) == 1)
				{
					//uint64_t mperf = measure_mperf_frequency();
					uint64_t aperf = measure_aperf_frequency();
					cpuFrequency = aperf;
				}
				// NOTE: tsc runs at the maccoeff (non turbo)
				//			*not* at the turbo frequency.
				maxcoef	 = bitfield(msr, 54, 49) / 2 + 4;
				currcoef = bitfield(msr, 5, 0) + 0x10;
				currdiv = 2 << bitfield(msr, 8, 6);
				
				break;
				
			case 0x05: /* K14 */
				msr = rdmsr64(K10_COFVID_STATUS);
				currcoef  = (bitfield(msr, 54, 49) + 0x10) << 2;
				currdiv = (bitfield(msr, 8, 4) + 1) << 2;
				currdiv += bitfield(msr, 3, 0);
				
				break;
				
			case 0x02: /* K11 */
				// not implimented
				break;
		}
		
		if (maxcoef)
		{
			if (currdiv)
			{
				if (!currcoef) currcoef = maxcoef;
				if (!cpuFrequency)
					fsbFrequency = ((tscFrequency * currdiv) / currcoef);
				else
					fsbFrequency = ((cpuFrequency * currdiv) / currcoef);
				
				DBG("%d.%d\n", currcoef / currdiv, ((currcoef % currdiv) * 100) / currdiv);
			} else {
				if (!cpuFrequency)
					fsbFrequency = (tscFrequency / maxcoef);
				else 
					fsbFrequency = (cpuFrequency / maxcoef);
				DBG("%d\n", currcoef);
			}
		}
		else if (currcoef)
		{
			if (currdiv)
			{
				fsbFrequency = ((tscFrequency * currdiv) / currcoef);
				DBG("%d.%d\n", currcoef / currdiv, ((currcoef % currdiv) * 100) / currdiv);
			} else {
				fsbFrequency = (tscFrequency / currcoef);
				DBG("%d\n", currcoef);
			}
		}
		if (!cpuFrequency) cpuFrequency = tscFrequency;
	}
	
#if 0
	if (!fsbFrequency) {
		fsbFrequency = (DEFAULT_FSB * 1000);
		cpuFrequency = tscFrequency;
		DBG("0 ! using the default value for FSB !\n");
	}
#endif
	
	p->CPU.MaxCoef = maxcoef;
	p->CPU.MaxDiv = maxdiv;
	p->CPU.CurrCoef = currcoef;
	p->CPU.CurrDiv = currdiv;
	p->CPU.TSCFrequency = tscFrequency;
	p->CPU.FSBFrequency = fsbFrequency;
	p->CPU.CPUFrequency = cpuFrequency;
	
	// keep formatted with spaces instead of tabs
	DBG("CPU: Brand String:             %s\n",              p->CPU.BrandString);
    DBG("CPU: Vendor/Family/ExtFamily:  0x%x/0x%x/0x%x\n",  p->CPU.Vendor, p->CPU.Family, p->CPU.ExtFamily);
    DBG("CPU: Model/ExtModel/Stepping:  0x%x/0x%x/0x%x\n",  p->CPU.Model, p->CPU.ExtModel, p->CPU.Stepping);
    DBG("CPU: MaxCoef/CurrCoef:         0x%x/0x%x\n",       p->CPU.MaxCoef, p->CPU.CurrCoef);
    DBG("CPU: MaxDiv/CurrDiv:           0x%x/0x%x\n",       p->CPU.MaxDiv, p->CPU.CurrDiv);
    DBG("CPU: TSCFreq:                  %dMHz\n",           p->CPU.TSCFrequency / 1000000);
    DBG("CPU: FSBFreq:                  %dMHz\n",           p->CPU.FSBFrequency / 1000000);
    DBG("CPU: CPUFreq:                  %dMHz\n",           p->CPU.CPUFrequency / 1000000);
    DBG("CPU: NoCores/NoThreads:        %d/%d\n",           p->CPU.NoCores, p->CPU.NoThreads);
    DBG("CPU: Features:                 0x%08x\n",          p->CPU.Features);
#if DEBUG_CPU
	pause();
#endif
}
Пример #7
0
BOOLEAN xmpReqSetRss(
  __in  NDIS_HANDLE         SynchronizeContext
  )
{
  USHORT                      i;
  UCHAR                      *pSecretKey;
  UCHAR                      *pTable;
  BOOLEAN                     bTable, bKey, bCpu, bHashInfo;
  BOOLEAN                     bQueue = FALSE;
  KIRQL                       OldIrql;
  xmpNicCtx_t                 *pNicCtx = SynchronizeContext;
  NDIS_RECEIVE_SCALE_PARAMETERS *pParams = &pNicCtx->ndisRssSet.params;
  static  int                 count = 0;

  XMPTRACE(XMP_DBG_WRN, ("==> xmpReqSetRss Count = %d Flags = 0x%8.8lx\n",
                         ++count, pParams->Flags));
  XF_GET_SLOCK(&pNicCtx->lock);

    pSecretKey = ((UCHAR *) pParams) + pParams->HashSecretKeyOffset;
    pTable = ((UCHAR *) pParams) + pParams->IndirectionTableOffset;
    bTable = bKey = bCpu = bHashInfo = FALSE;

    if ( XMP_NIC_RSS_IS_ENABLED(pNicCtx) &&
         !(bit(pParams->Flags, NDIS_RSS_PARAM_FLAG_DISABLE_RSS)) )
    {
      if ( !(bit(pParams->Flags, NDIS_RSS_PARAM_FLAG_HASH_KEY_UNCHANGED)) )
        bKey = TRUE;

      if ( !(bit(pParams->Flags, NDIS_RSS_PARAM_FLAG_ITABLE_UNCHANGED)) )
        bTable = TRUE;

       if ( !(bit(pParams->Flags, NDIS_RSS_PARAM_FLAG_BASE_CPU_UNCHANGED )) )
        bCpu = TRUE;

    }
    else
    {
      bTable = bKey = bCpu = bHashInfo = TRUE;
      pNicCtx->RssParamsReq.HashFunction = 0;
    }

    /* Enable RTH_CFG, RTS_ENHANCED and RMAC_STRIP_FCS to 0 */
    if ( bHashInfo )
    {
      pNicCtx->RssParamsReq.HashType               = 
        NDIS_RSS_HASH_TYPE_FROM_HASH_INFO(pParams->HashInformation);
      pNicCtx->RssParamsReq.HashFunction               = 
        NDIS_RSS_HASH_FUNC_FROM_HASH_INFO(pParams->HashInformation);
    }

    if ( NDIS_RSS_HASH_FUNC_FROM_HASH_INFO(pParams->HashInformation) != 0 )
    {
      if( bCpu )
        pNicCtx->RssParamsReq.BaseCpuNum = pParams->BaseCpuNumber;

      if ( bTable )
      {
        pNicCtx->RssParamsReq.TableSz      =
          pParams->IndirectionTableSize > XMP_NIC_RSS_MAX_TABLE_SZ ?
          XMP_NIC_RSS_MAX_TABLE_SZ : pParams->IndirectionTableSize;
        {
          ULONG TableSz =  pNicCtx->RssParamsReq.TableSz;
          USHORT NumLsbs = 0;
          while (TableSz != 1)
          {  
            TableSz = TableSz>>1;                                         
            NumLsbs++;
          } 
          pNicCtx->RssParamsReq.HashBitsSz = NumLsbs;
        }

        NdisMoveMemory(pNicCtx->RssParamsReq.Table, pTable,
                       pNicCtx->RssParamsReq.TableSz);
      }

      if ( bKey )
      {
        pNicCtx->RssParamsReq.SecretKeySz  = pParams->HashSecretKeySize;
        NdisMoveMemory(pNicCtx->RssParamsReq.SecretKey, pSecretKey,
                       pNicCtx->RssParamsReq.SecretKeySz);
      }
    }
    pNicCtx->RssParamsReq.Flags = pParams->Flags;

    KeMemoryBarrier();
    if ( !pNicCtx->wiQueued )
    {
      pNicCtx->wiQueued = TRUE;
      if ( !pNicCtx->wiRunning )
        bQueue = TRUE;
    }
  XF_FREE_SLOCK(&pNicCtx->lock);

#ifdef XMP_SET_RSS_IN_WORKER
  if ( bQueue )
    NdisQueueIoWorkItem(pNicCtx->hSetRssWI, 
                        (NDIS_IO_WORKITEM_ROUTINE)xmpNicSetRssParameters,
                        pNicCtx);
#else
    xmpNicSetRssParameters(pNicCtx, NULL);
#endif

  XMPTRACE(XMP_DBG_WRN, ("<== xmpReqSetRss\n"));
  return TRUE;
}
Пример #8
0
void ks0108_displaystate(unsigned char state)
{
	ks0108_writedata((state ? bit(0) : 0) | bit(1) | bit(2) | bit(3) | bit(4) | bit(5));
}
Пример #9
0
void Builder::processLBlockSet(WorkSpace *fw, otawa::ccg::LBlockSet *lbset) {
	ASSERT(fw);
	ASSERT(lbset);
	const hard::Cache *cache = hard::CACHE_CONFIGURATION(fw)->instCache();

	// Create the CCG
	Collection *ccgs = Graph::GRAPHS(fw);
	if(!ccgs) {
		ccgs = new Collection(cache->rowCount());
		fw->addProp(new DeletableProperty<Collection *>(Graph::GRAPHS, ccgs));
	}
	Graph *ccg = new Graph;
	ccgs->ccgs[lbset->line()] = ccg;

	// Initialization
	for(LBlockSet::Iterator lblock(*lbset); lblock; lblock++) {
		Node *node = new Node(lblock);
		ccg->add(node);
		Graph::NODE(lblock) = node;
	}

	// Run the DFA
	Problem prob(lbset, lbset->count(), cache, fw);
	const CFGCollection *coll = INVOLVED_CFGS(fw);
	dfa::XCFGVisitor<Problem> visitor(*coll, prob);
	dfa::XIterativeDFA<dfa::XCFGVisitor<Problem> > engine(visitor);
	engine.process();

	// Add the annotations from the DFA result
	for (CFGCollection::Iterator cfg(coll); cfg; cfg++) {
		for (CFG::BBIterator block(*cfg); block; block++) {
			dfa::XCFGVisitor<Problem>::key_t pair(*cfg, *block);
			dfa::BitSet *bitset = engine.in(pair);
			block->addProp(new DeletableProperty<dfa::BitSet *>(IN, new dfa::BitSet(*bitset)));
		}
	}

	// Detecting the non conflict state of each lblock
	BasicBlock *BB;
	LBlock *line;
	int length = lbset->count();
	for(LBlockSet::Iterator lbloc(*lbset); lbloc; lbloc++)
		if(lbloc->id() != 0 && lbloc->id() != length - 1) {
			BB = lbloc->bb();
			dfa::BitSet *inid = IN(BB);
			for(dfa::BitSet::Iterator bit(*inid); bit; bit++)
				line = lbset->lblock(*bit);
				if(cache->block(line->address()) == cache->block(lbloc->address())
					&& BB != line->bb())
					NON_CONFLICT(lbloc) = true;

		}

	// Building the ccg edges using DFA
	length = lbset->count();
	address_t adinst;
	LBlock *aux;

	for (CFGCollection::Iterator cfg(coll); cfg; cfg++) {
		for (CFG::BBIterator bb(*cfg); bb; bb++) {
			if ((cfg != ENTRY_CFG(fw)) || (!bb->isEntry() && !bb->isExit())) {
				dfa::BitSet *info = IN(bb);
				ASSERT(info);
				bool test = false;
				bool visit;
				for(BasicBlock::InstIter inst(bb); inst; inst++) {
					visit = false;
					adinst = inst->address();
					for (LBlockSet::Iterator lbloc(*lbset); lbloc; lbloc++){
						address_t address = lbloc->address();
						// the first lblock in the BB it's a conflict
						if(adinst == address && !test && bb == lbloc->bb()) {
							for (int i = 0; i< length; i++)
								if (info->contains(i)) {
									LBlock *lblock = lbset->lblock(i);
									Node *node = Graph::NODE(lblock);
									new Edge (node, Graph::NODE(lbloc));
								}
							aux = lbloc;
							test = true;
							visit = true;
							break;
						}

						if(adinst == address && !visit && bb == lbloc->bb()) {
							new Edge(Graph::NODE(aux), Graph::NODE(lbloc));
							aux = lbloc;
							break;
						}
					}
				}
			}
		}
	}

	// build edge to LBlock end
	BasicBlock *exit = ENTRY_CFG(fw)->exit();
	LBlock *end = lbset->lblock(length-1);
	dfa::BitSet *info = IN(exit);
	for (int i = 0; i< length; i++)
		if (info->contains(i)) {
			LBlock *ccgnode1 = lbset->lblock(i);
			new Edge(Graph::NODE(ccgnode1), Graph::NODE(end));
		}

	// Build edge from 'S' till 'end'
	LBlock *s = lbset->lblock(0);
	new Edge(Graph::NODE(s), Graph::NODE(end));

	// Cleanup the DFA annotations
	for (CFGCollection::Iterator cfg(coll); cfg; cfg++)
		for (CFG::BBIterator block(cfg); block; block++)
			block->removeProp(&IN);
}
// Scans the keys, and puts their states in _key_states_raw for debouncing
void CoreScanner::_scan_keys()
{
  _set_pin(_A, 3); _set_pin(_B, 0); _set_pin(_C, 2); delayMicroseconds(8); _key_states_raw[0] = !bit_get(PINB, bit(_A));
  _set_pin(_B, 3); _set_pin(_A, 0); _set_pin(_C, 2); delayMicroseconds(8); _key_states_raw[1] = !bit_get(PINB, bit(_B));
  _set_pin(_A, 3); _set_pin(_C, 0); _set_pin(_B, 2); delayMicroseconds(8); _key_states_raw[2] = !bit_get(PINB, bit(_A));
  _set_pin(_C, 3); _set_pin(_A, 0); _set_pin(_B, 2); delayMicroseconds(8); _key_states_raw[3] = !bit_get(PINB, bit(_C));
  _set_pin(_B, 3); _set_pin(_C, 0); _set_pin(_A, 2); delayMicroseconds(8); _key_states_raw[4] = !bit_get(PINB, bit(_B));
  _set_pin(_C, 3); _set_pin(_B, 0); _set_pin(_A, 2); delayMicroseconds(8); _key_states_raw[5] = !bit_get(PINB, bit(_C));
}
Пример #11
0
void ks0108_writecontrol(unsigned char byte)
{
	udelay(ks0108_delay);
	parport_write_control(ks0108_parport, byte ^ (bit(0) | bit(1) | bit(3)));
}
Пример #12
0
	NULL,
	"SELECT",
	"INSERT",
	"REPLACE",
	"UPDATE",
	"DELETE",
	"CALL",
	"AUTH",
	"EVAL",
	"UPSERT",
};

#define bit(c) (1ULL<<IPROTO_##c)
const uint64_t iproto_body_key_map[IPROTO_UPSERT + 1] = {
	0,                                                     /* unused */
	bit(SPACE_ID) | bit(LIMIT) | bit(KEY),                 /* SELECT */
	bit(SPACE_ID) | bit(TUPLE),                            /* INSERT */
	bit(SPACE_ID) | bit(TUPLE),                            /* REPLACE */
	bit(SPACE_ID) | bit(KEY) | bit(TUPLE),                 /* UPDATE */
	bit(SPACE_ID) | bit(KEY),                              /* DELETE */
	bit(FUNCTION_NAME) | bit(TUPLE),                       /* CALL */
	bit(USER_NAME)| bit(TUPLE),                            /* AUTH */
	bit(EXPR)     | bit(TUPLE),                            /* EVAL */
	bit(SPACE_ID) | bit(OPS) | bit(TUPLE),                 /* UPSERT */
};
#undef bit

const char *iproto_key_strs[IPROTO_KEY_MAX] = {
	"type",             /* 0x00 */
	"sync",             /* 0x01 */
	"server_id",          /* 0x02 */
Пример #13
0
void ConstBCFunction::operator()(FArrayBox&           a_state,
                                 const Box&           a_valid,
                                 const ProblemDomain& a_domain,
                                 Real                 a_dx,
                                 bool                 a_homogeneous)
{
  const Box& domainBox = a_domain.domainBox();

  for (int idir = 0; idir < SpaceDim; idir++)
  {
    if (!a_domain.isPeriodic(idir))
    {
      for (SideIterator sit; sit.ok(); ++sit)
      {
        Side::LoHiSide side = sit();

        if (a_valid.sideEnd(side)[idir] == domainBox.sideEnd(side)[idir])
        {
          int  bcType;
          Real bcValue;

          if (side == Side::Lo)
          {
            bcType  = m_loSideType [idir];
            bcValue = m_loSideValue[idir];
          }
          else
          {
            bcType  = m_hiSideType [idir];
            bcValue = m_hiSideValue[idir];
          }

          if (bcType == 0)
          {
            // Neumann BC
            int isign = sign(side);

            Box toRegion = adjCellBox(a_valid, idir, side, 1);
            toRegion &= a_state.box();

            Box fromRegion = toRegion;
            fromRegion.shift(idir, -isign);

            a_state.copy(a_state, fromRegion, 0, toRegion, 0, a_state.nComp());

            if (!a_homogeneous)
            {
              for (BoxIterator bit(toRegion); bit.ok(); ++bit)
              {
                const IntVect& ivTo = bit();
                // IntVect ivClose = ivTo - isign*BASISV(idir);

                for (int icomp = 0; icomp < a_state.nComp(); icomp++)
                {
                  a_state(ivTo, icomp) += Real(isign)*a_dx*bcValue;
                }
              }
            }
          }
          else if (bcType == 1)
          {
            // Dirichlet BC
            int isign = sign(side);

            Box toRegion = adjCellBox(a_valid, idir, side, 1);
            toRegion &= a_state.box();

            for (BoxIterator bit(toRegion); bit.ok(); ++bit)
            {
              const IntVect& ivTo = bit();

              IntVect ivClose = ivTo -   isign*BASISV(idir);
              // IntVect ivFar   = ivTo - 2*isign*BASISV(idir);

              Real inhomogVal = 0.0;

              if (!a_homogeneous)
              {
                inhomogVal = bcValue;
              }

              for (int icomp = 0; icomp < a_state.nComp(); icomp++)
              {
                Real nearVal = a_state(ivClose, icomp);
                // Real farVal  = a_state(ivFar,   icomp);

                Real ghostVal = linearInterp(inhomogVal, nearVal);

                a_state(ivTo, icomp) = ghostVal;
              }
            }
          }
          else
          {
            MayDay::Abort("ConstBCFunction::operator() - unknown BC type");
          }
        } // if ends match
      } // end loop over sides
    } // if not periodic in this direction
  } // end loop over directions
}
Пример #14
0
// recursiveReplicateDim:
//   d = dimension
//   ea.sizeOfDimension(d)/2 <= extent <= ea.sizeOfDimension(d),
//     only positions [0..extent) are non-zero
//   1 <= 2^k <= extent: size of current interval
//   0 <= pos < ea.sizeOfDimension(d): relative position of first vector
//   0 <= limit < ea.sizeOfDimension(): max # of positions to process
//   dimProd: product of dimensions 0..d
//   recBound: recursion bound (controls noise) 
//
// SHAI: limit and extent are always the same, it seems
static
void recursiveReplicateDim(const EncryptedArray& ea, const Ctxt& ctxt, 
                           long d, long extent, long k, long pos, long limit,  
                           long dimProd, long recBound,
                           RepAuxDim& repAux,
                           ReplicateHandler *handler)
{
  if (pos >= limit) return;

  if (replicateVerboseFlag) { // DEBUG code
    cerr << "check: " << k; CheckCtxt(ctxt, "");
  }
  
  long dSize = ea.sizeOfDimension(d);
  long nSlots = ea.size();

  if (k == 0) { // last level in this dimension: blocks of size 2^k=1

    if ( extent >= dSize) { // nothing to do in this dimension
      replicateAllNextDim(ea, ctxt, d+1, dimProd, recBound, repAux, handler);
      return;
    } // SHAI: Will we ever have extent > dSize??

    // need to replicate to fill positions [ (1L << n) .. dSize-1 ]

    if (repAux.tab(d,0).null()) { // generate mask if not there already
      ZZX mask;
      SelectRangeDim(ea, mask, 0, dSize - extent, d);
      repAux.tab(d, 0).set_ptr(new DoubleCRT(mask, ea.getContext()));
    }

    Ctxt ctxt_tmp = ctxt;
    ctxt_tmp.multByConstant(*repAux.tab(d, 0));

    ea.rotate1D(ctxt_tmp, d, extent, /*don't-care-flag=*/true);
    ctxt_tmp += ctxt;
    replicateAllNextDim(ea, ctxt_tmp, d+1, dimProd, recBound, repAux, handler);
    return;
  }

  // If we need to stop early, call the handler
  if (handler->earlyStop(d, k, dimProd)) {
    handler->handle(ctxt);
    return;
  }

  k--;
  Ctxt ctxt_masked = ctxt;

  {   // artificial scope to miminize storage in the recursion
    { // another artificial scope (SHAI: this seems redundant)

      // generate mask at index k+1, if not there yet

      if (repAux.tab(d, k+1).null()) { // need to generate
        vector< long > maskArray(nSlots,0);
        for (long i = 0; i < nSlots; i++) {
          long c = ea.coordinate(d, i);
          if (c < extent && bit(c, k) == 0)
            maskArray[i] = 1;
        }
	// store this mask in the repAux table
        ZZX mask;
        ea.encode(mask, maskArray);
        repAux.tab(d, k+1).set_ptr(new DoubleCRT(mask, ea.getContext()));
      }

      // Apply mask to zero out slots in ctxt
      ctxt_masked.multByConstant(*repAux.tab(d, k+1));
    }

    Ctxt ctxt_left = ctxt_masked;
    ea.rotate1D(ctxt_left, d, 1L << k, /*don't-care-flag=*/true);
    ctxt_left += ctxt_masked;

    recursiveReplicateDim(ea, ctxt_left, d, extent, k, pos, limit, 
                          dimProd, recBound, repAux, handler);
  }

  pos += (1L << k);
  if (pos >= limit)
    return;

  Ctxt ctxt_right = ctxt;
  ctxt_right -= ctxt_masked; 
  ctxt_masked = ctxt_right; // reuse ctxt_masked as a temp
  ea.rotate1D(ctxt_masked, d, -(1L << k), /*don't-care-flag=*/true);
  ctxt_right += ctxt_masked;

  recursiveReplicateDim(ea, ctxt_right, d, extent, k, pos, limit, 
                        dimProd, recBound, repAux, handler);
}
Пример #15
0
GT PFC::multi_miller(int n,G2** QQ,G1** PP)
{
	GT z;
    ZZn *Px,*Py;
	int i,j,*k,nb;
    ECn3 *Q,*A,*A2;
	ECn P;
    ZZn18 res,rd;
	Big m;
	Big X=*x;

	Px=new ZZn[n];
	Py=new ZZn[n];
	Q=new ECn3[n];
	A=new ECn3[n];
	A2=new ECn3[n];
	k=new int[n];

	m=X/7;

    nb=bits(m);
	res=1; 

	for (j=0;j<n;j++)
	{
		k[j]=0;
		P=PP[j]->g; normalise(P); Q[j]=QQ[j]->g; 
		extract(P,Px[j],Py[j]);
	}

	for (j=0;j<n;j++) A[j]=Q[j];

	for (i=nb-2;i>=0;i--)
	{
		res*=res;
		for (j=0;j<n;j++)
		{
			if (QQ[j]->ptable==NULL)
				res*=g(A[j],A[j],Px[j],Py[j]);
			else
				res*=gp(QQ[j]->ptable,k[j],Px[j],Py[j]);
		}
		if (bit(m,i)==1)
			for (j=0;j<n;j++) 
			{
				if (QQ[j]->ptable==NULL)
					res*=g(A[j],Q[j],Px[j],Py[j]);
				else
					res*=gp(QQ[j]->ptable,k[j],Px[j],Py[j]);
			}
		if (res.iszero()) return 0;  
	}

	rd=res;
	res*=res;

	for (j=0;j<n;j++)
	{
		
		if (QQ[j]->ptable==NULL) 
		{
			Q[j]=A[j];
			res*=g(A[j],A[j],Px[j],Py[j]);
		}
		else res*=gp(QQ[j]->ptable,k[j],Px[j],Py[j]);
	}

	rd*=res;

	for (j=0;j<n;j++)
	{
		
		if (QQ[j]->ptable==NULL)
		{
			A2[j]=A[j];
			rd*=g(A[j],Q[j],Px[j],Py[j]);
		}
		else rd*=gp(QQ[j]->ptable,k[j],Px[j],Py[j]);
	}
	
	res*=Frobenius(rd,*frob,6);

	for (j=0;j<n;j++)
	{
		if (QQ[j]->ptable==NULL)
		{
			A[j]=psi(A[j],*frob,6);
			res*=g(A[j],A2[j],Px[j],Py[j]);
		}
		else 
			res*=gp(QQ[j]->ptable,k[j],Px[j],Py[j]);
	}

	delete [] k;
	delete [] A2;
	delete [] A;
	delete [] Q;
	delete [] Py;
	delete [] Px;

	z.g=res;
	return z;
}
Пример #16
0
BOOL ate(ECn3& Q,ECn& P,Big &x,ZZn2& X,ZZn6& res)
{ 
    int i,j,n,nb,nbw,nzs;
    ECn3 A;
	ZZn Px,Py;
    ZZn6 w;
	Big q=x*x-x+1;

#ifdef MR_COUNT_OPS
fpc=fpa=fpx=0;
#endif  

	normalise(P);
	Q.norm();
	extract(P,Px,Py);

    Px+=Px;  // because x^6+2 is irreducible.. simplifies line function calculation
    Py+=Py; 

    res=1;  
    A=Q;    // reset A
    nb=bits(x);
	res.mark_as_miller();

    for (i=nb-2;i>=0;i--)
    {
		res*=res;
		res*=g(A,A,Px,Py);
		if (bit(x,i)==1)
			res*=g(A,Q,Px,Py);
        if (res.iszero()) return FALSE;  
    }

#ifdef MR_COUNT_OPS
printf("After Miller  fpc= %d fpa= %d fpx= %d\n",fpc,fpa,fpx);
#endif
  //  if (!A.iszero() || res.iszero()) return FALSE;

    w=res;   
    w.powq(X);
    res*=w;                        // ^(p+1)

    w=res;
    w.powq(X); w.powq(X); w.powq(X);
    res=w/res;                     // ^(p^3-1)

// exploit the clever "trick" for a half-length exponentiation!

    res.mark_as_unitary();

    w=res;
    res.powq(X);  // res*=res;  // res=pow(res,CF);
 
    if (x<0) res/=powu(w,-x);
    else res*=powu(w,x);
#ifdef MR_COUNT_OPS
printf("After pairing fpc= %d fpa= %d fpx= %d\n",fpc,fpa,fpx);
fpa=fpc=fpx=0;
#endif

    if (res==(ZZn6)1) return FALSE;
    return TRUE;            
}
Пример #17
0
GT PFC::miller_loop(const G2& QQ,const G1& PP)
{ 
	GT z;
	Big n;
	int i,j,nb,nbw,nzs;
    ECn3 A,m2A,Q;
	ECn P;
	ZZn Px,Py;
	BOOL precomp;
    ZZn18 r,rd;
	Big X=*x;

	Q=QQ.g; P=PP.g;

	precomp=FALSE;
	if (QQ.ptable!=NULL) precomp=TRUE;

	normalise(P);
	extract(P,Px,Py);

	A=Q;
	n=(X/7);

	nb=bits(n);
	r=1; j=0;
	r.mark_as_miller();
	for (i=nb-2;i>=0;i--)
    {
        r*=r;  
		if (precomp) r*=gp(QQ.ptable,j,Px,Py);
        else         r*=g(A,A,Px,Py);
        if (bit(n,i)) 
		{
			if (precomp) r*=gp(QQ.ptable,j,Px,Py);
            else         r*=g(A,Q,Px,Py);
		}
    }

	rd=r;
	r*=r;

	Q=A;
	if (precomp) r*=gp(QQ.ptable,j,Px,Py);
	else         r*=g(A,A,Px,Py);

	rd*=r;

	m2A=A;
	if (precomp) rd*=gp(QQ.ptable,j,Px,Py);
	else		 rd*=g(A,Q,Px,Py);

	r*=Frobenius(rd,*frob,6);
	if (precomp) r*=gp(QQ.ptable,j,Px,Py);
	else
	{
		A=psi(A,*frob,6);
		r*=g(A,m2A,Px,Py);
	}
	
	z.g=r;
	return z;
}
Пример #18
0
 const scalarval& operator[]( int index ) const {
     return bit( index );
 }
Пример #19
0
void ClassDiagram::writeFigure(FTextStream &output,const char *path,
                               const char *fileName) const
{
  uint baseRows=base->computeRows();
  uint superRows=super->computeRows();
  uint baseMaxX, baseMaxLabelWidth, superMaxX, superMaxLabelWidth;
  base->computeExtremes(&baseMaxLabelWidth,&baseMaxX);
  super->computeExtremes(&superMaxLabelWidth,&superMaxX);

  uint rows=baseRows+superRows-1;
  uint cols=(QMAX(baseMaxX,superMaxX)+gridWidth*2-1)/gridWidth;
  
  // Estimate the image aspect width and height in pixels.
  uint estHeight = rows*40;
  uint estWidth  = cols*(20+QMAX(baseMaxLabelWidth,superMaxLabelWidth));
  //printf("Estimated size %d x %d\n",estWidth,estHeight);
  
  const float pageWidth = 14.0f; // estimated page width in cm.
                                 // Somewhat lower to deal with estimation
                                 // errors. 
  
  // compute the image height in centimeters based on the estimates
  float realHeight = QMIN(rows,12); // real height in cm
  float realWidth  = realHeight * estWidth/(float)estHeight;
  if (realWidth>pageWidth) // assume that the page width is about 15 cm
  {
    realHeight*=pageWidth/realWidth; 
    realWidth=pageWidth;
  }

  //output << "}\n";
  output << "\\begin{figure}[H]\n"
            "\\begin{center}\n"
            "\\leavevmode\n";
  output << "\\includegraphics[height=" << realHeight << "cm]{" 
                                        << fileName << "}" << endl;
  output << "\\end{center}\n"
            "\\end{figure}\n";
  
  //printf("writeFigure rows=%d cols=%d\n",rows,cols);

  QCString epsBaseName=(QCString)path+"/"+fileName;
  QCString epsName=epsBaseName+".eps";
  QFile f1;
  f1.setName(epsName.data());
  if (!f1.open(IO_WriteOnly))
  {
    err("Could not open file %s for writing\n",f1.name().data());
    exit(1);
  }
  FTextStream t(&f1);
  
  //printf("writeEPS() rows=%d cols=%d\n",rows,cols);
  
  // generate EPS header and postscript variables and procedures
  
  t << "%!PS-Adobe-2.0 EPSF-2.0\n";
  t << "%%Title: ClassName\n";
  t << "%%Creator: Doxygen\n";
  t << "%%CreationDate: Time\n";
  t << "%%For: \n";
  t << "%Magnification: 1.00\n";
  t << "%%Orientation: Portrait\n";
  t << "%%BoundingBox: 0 0 500 " << estHeight*500.0/(float)estWidth << "\n";
  t << "%%Pages: 0\n";
  t << "%%BeginSetup\n";
  t << "%%EndSetup\n";
  t << "%%EndComments\n";
  t << "\n";
  t << "% ----- variables -----\n";
  t << "\n";
  t << "/boxwidth 0 def\n";
  t << "/boxheight 40 def\n";
  t << "/fontheight 24 def\n";
  t << "/marginwidth 10 def\n";
  t << "/distx 20 def\n";
  t << "/disty 40 def\n";
  t << "/boundaspect " << estWidth/(float)estHeight << " def  % aspect ratio of the BoundingBox (width/height)\n";
  t << "/boundx 500 def\n";
  t << "/boundy boundx boundaspect div def\n";
  t << "/xspacing 0 def\n";
  t << "/yspacing 0 def\n";
  t << "/rows " << rows << " def\n";
  t << "/cols " << cols << " def\n";
  t << "/scalefactor 0 def\n";
  t << "/boxfont /Times-Roman findfont fontheight scalefont def\n";
  t << "\n";
  t << "% ----- procedures -----\n";
  t << "\n";
  t << "/dotted { [1 4] 0 setdash } def\n";
  t << "/dashed { [5] 0 setdash } def\n";
  t << "/solid  { [] 0 setdash } def\n";
  t << "\n";
  t << "/max % result = MAX(arg1,arg2)\n";
  t << "{\n";
  t << "  /a exch def\n";
  t << "  /b exch def\n";
  t << "  a b gt {a} {b} ifelse\n";
  t << "} def\n";
  t << "\n";
  t << "/xoffset % result = MAX(0,(scalefactor-(boxwidth*cols+distx*(cols-1)))/2)\n";
  t << "{\n";
  t << "  0 scalefactor boxwidth cols mul distx cols 1 sub mul add sub 2 div max\n";
  t << "} def\n";
  t << "\n";
  t << "/cw % boxwidth = MAX(boxwidth, stringwidth(arg1))\n";
  t << "{\n";
  t << "  /str exch def\n";
  t << "  /boxwidth boxwidth str stringwidth pop max def\n";
  t << "} def\n";
  t << "\n";
  t << "/box % draws a box with text `arg1' at grid pos (arg2,arg3)\n";
  t << "{ gsave\n";
  t << "  2 setlinewidth\n";
  t << "  newpath\n";
  t << "  exch xspacing mul xoffset add\n";
  t << "  exch yspacing mul\n";
  t << "  moveto\n";
  t << "  boxwidth 0 rlineto \n";
  t << "  0 boxheight rlineto \n";
  t << "  boxwidth neg 0 rlineto \n";
  t << "  0 boxheight neg rlineto \n";
  t << "  closepath\n";
  t << "  dup stringwidth pop neg boxwidth add 2 div\n";
  t << "  boxheight fontheight 2 div sub 2 div\n";
  t << "  rmoveto show stroke\n";
  t << "  grestore\n";
  t << "} def  \n";
  t << "\n";
  t << "/mark\n";
  t << "{ newpath\n";
  t << "  exch xspacing mul xoffset add boxwidth add\n";
  t << "  exch yspacing mul\n";
  t << "  moveto\n";
  t << "  0 boxheight 4 div rlineto\n";
  t << "  boxheight neg 4 div boxheight neg 4 div rlineto\n";
  t << "  closepath\n";
  t << "  eofill\n";
  t << "  stroke\n";
  t << "} def\n";
  t << "\n";
  t << "/arrow\n";
  t << "{ newpath\n";
  t << "  moveto\n";
  t << "  3 -8 rlineto\n";
  t << "  -6 0 rlineto\n";
  t << "  3 8 rlineto\n";
  t << "  closepath\n";
  t << "  eofill\n";
  t << "  stroke\n";
  t << "} def\n";
  t << "\n";
  t << "/out % draws an output connector for the block at (arg1,arg2)\n";
  t << "{\n";
  t << "  newpath\n";
  t << "  exch xspacing mul xoffset add boxwidth 2 div add\n";
  t << "  exch yspacing mul boxheight add\n";
  t << "  /y exch def\n";
  t << "  /x exch def\n";
  t << "  x y moveto\n";
  t << "  0 disty 2 div rlineto \n";
  t << "  stroke\n";
  t << "  1 eq { x y disty 2 div add arrow } if\n";
  t << "} def\n";
  t << "\n";
  t << "/in % draws an input connector for the block at (arg1,arg2)\n";
  t << "{\n";
  t << "  newpath\n";
  t << "  exch xspacing mul xoffset add boxwidth 2 div add\n";
  t << "  exch yspacing mul disty 2 div sub\n";
  t << "  /y exch def\n";
  t << "  /x exch def\n";
  t << "  x y moveto\n";
  t << "  0 disty 2 div rlineto\n";
  t << "  stroke\n";
  t << "  1 eq { x y disty 2 div add arrow } if\n";
  t << "} def\n";
  t << "\n";
  t << "/hedge\n";
  t << "{\n";
  t << "  exch xspacing mul xoffset add boxwidth 2 div add\n";
  t << "  exch yspacing mul boxheight 2 div sub\n";
  t << "  /y exch def\n";
  t << "  /x exch def\n";
  t << "  newpath\n";
  t << "  x y moveto\n";
  t << "  boxwidth 2 div distx add 0 rlineto\n";
  t << "  stroke\n";
  t << "  1 eq\n";
  t << "  { newpath x boxwidth 2 div distx add add y moveto\n";
  t << "    -8 3 rlineto\n";
  t << "    0 -6 rlineto\n";
  t << "    8 3 rlineto\n";
  t << "    closepath\n";
  t << "    eofill\n";
  t << "    stroke\n";
  t << "  } if\n";
  t << "} def\n";
  t << "\n";
  t << "/vedge\n";
  t << "{\n";
  t << "  /ye exch def\n";
  t << "  /ys exch def\n";
  t << "  /xs exch def\n";
  t << "  newpath\n";
  t << "  xs xspacing mul xoffset add boxwidth 2 div add dup\n";
  t << "  ys yspacing mul boxheight 2 div sub\n";
  t << "  moveto\n";
  t << "  ye yspacing mul boxheight 2 div sub\n";
  t << "  lineto\n";
  t << "  stroke\n";
  t << "} def\n";
  t << "\n";
  t << "/conn % connections the blocks from col `arg1' to `arg2' of row `arg3'\n";
  t << "{\n";
  t << "  /ys exch def\n";
  t << "  /xe exch def\n";
  t << "  /xs exch def\n";
  t << "  newpath\n";
  t << "  xs xspacing mul xoffset add boxwidth 2 div add\n";
  t << "  ys yspacing mul disty 2 div sub\n";
  t << "  moveto\n";
  t << "  xspacing xe xs sub mul 0\n";
  t << "  rlineto\n";
  t << "  stroke\n";
  t << "} def\n";
  t << "\n";
  t << "% ----- main ------\n";
  t << "\n";
  t << "boxfont setfont\n";
  t << "1 boundaspect scale\n";


  bool done=FALSE;
  QListIterator<DiagramRow> bit(*base);
  DiagramRow *dr;
  for (;(dr=bit.current()) && !done;++bit)
  {
    QListIterator<DiagramItem> rit(*dr);
    DiagramItem *di;
    for (;(di=rit.current());++rit)
    {
      done=di->isInList();
      t << "(" << di->label() << ") cw\n";
    }
  }
  QListIterator<DiagramRow> sit(*super);
  ++sit;
  done=FALSE;
  for (;(dr=sit.current()) && !done;++sit)
  {
    QListIterator<DiagramItem> rit(*dr);
    DiagramItem *di;
    for (;(di=rit.current());++rit)
    {
      done=di->isInList();
      t << "(" << di->label() << ") cw\n";
    }
  }

  t << "/boxwidth boxwidth marginwidth 2 mul add def\n"
    << "/xspacing boxwidth distx add def\n"
    << "/yspacing boxheight disty add def\n"
    << "/scalefactor \n"
    << "  boxwidth cols mul distx cols 1 sub mul add\n"
    << "  boxheight rows mul disty rows 1 sub mul add boundaspect mul \n"
    << "  max def\n"
    << "boundx scalefactor div boundy scalefactor div scale\n";
  
  t << "\n% ----- classes -----\n\n";
  base->drawBoxes(t,0,TRUE,FALSE,baseRows,superRows,0,0);
  super->drawBoxes(t,0,FALSE,FALSE,baseRows,superRows,0,0);
  
  t << "\n% ----- relations -----\n\n";
  base->drawConnectors(t,0,TRUE,FALSE,baseRows,superRows,0,0);
  super->drawConnectors(t,0,FALSE,FALSE,baseRows,superRows,0,0);

  f1.close();
  if (Config_getBool(USE_PDFLATEX))
  {
    QCString epstopdfArgs(4096);
    epstopdfArgs.sprintf("\"%s.eps\" --outfile=\"%s.pdf\"",
                   epsBaseName.data(),epsBaseName.data());
    //printf("Converting eps using `%s'\n",epstopdfArgs.data());
    portable_sysTimerStart();
    if (portable_system("epstopdf",epstopdfArgs)!=0)
    {
       err("Problems running epstopdf. Check your TeX installation!\n");
       portable_sysTimerStop();
       return;
    }
    portable_sysTimerStop();
  }
}
Пример #20
0
// Executes one line of 0-terminated G-Code. The line is assumed to contain only uppercase
// characters and signed floating point values (no whitespace). Comments and block delete
// characters have been removed. All units and positions are converted and exported to grbl's
// internal functions in terms of (mm, mm/min) and absolute machine coordinates, respectively.
uint8_t gc_execute_line(char *line) 
{
  uint8_t char_counter = 0;  
  char letter;
  double value;
  int int_value;
  
  uint16_t modal_group_words = 0;  // Bitflag variable to track and check modal group words in block
  uint8_t axis_words = 0;          // Bitflag to track which XYZ(ABC) parameters exist in block

  double inverse_feed_rate = -1; // negative inverse_feed_rate means no inverse_feed_rate specified
  uint8_t absolute_override = false; // true(1) = absolute motion for this block only {G53}
  uint8_t non_modal_action = NON_MODAL_NONE; // Tracks the actions of modal group 0 (non-modal)
  
  double target[3], offset[3];  
  clear_vector(target); // XYZ(ABC) axes parameters.
  clear_vector(offset); // IJK Arc offsets are incremental. Value of zero indicates no change.
    
  gc.status_code = STATUS_OK;
  
  /* Pass 1: Commands and set all modes. Check for modal group violations.
     NOTE: Modal group numbers are defined in Table 4 of NIST RS274-NGC v3, pg.20 */
  uint8_t group_number = MODAL_GROUP_NONE;
  while(next_statement(&letter, &value, line, &char_counter)) {
    int_value = trunc(value);
    switch(letter) {
      case 'G':
        // Set modal group values
        switch(int_value) {
          case 4: case 10: case 28: case 30: case 53: case 92: group_number = MODAL_GROUP_0; break;
          case 0: case 1: case 2: case 3: case 80: group_number = MODAL_GROUP_1; break;
          case 17: case 18: case 19: group_number = MODAL_GROUP_2; break;
          case 90: case 91: group_number = MODAL_GROUP_3; break;
          case 93: case 94: group_number = MODAL_GROUP_5; break;
          case 20: case 21: group_number = MODAL_GROUP_6; break;
          case 54: case 55: case 56: case 57: case 58: case 59: group_number = MODAL_GROUP_12; break;
        }          
        // Set 'G' commands
        switch(int_value) {
          case 0: gc.motion_mode = MOTION_MODE_SEEK; break;
          case 1: gc.motion_mode = MOTION_MODE_LINEAR; break;
          case 2: gc.motion_mode = MOTION_MODE_CW_ARC; break;
          case 3: gc.motion_mode = MOTION_MODE_CCW_ARC; break;
          case 4: non_modal_action = NON_MODAL_DWELL; break;
          case 10: non_modal_action = NON_MODAL_SET_COORDINATE_DATA; break;
          case 17: select_plane(X_AXIS, Y_AXIS, Z_AXIS); break;
          case 18: select_plane(X_AXIS, Z_AXIS, Y_AXIS); break;
          case 19: select_plane(Y_AXIS, Z_AXIS, X_AXIS); break;
          case 20: gc.inches_mode = true; break;
          case 21: gc.inches_mode = false; break;
          case 28: case 30: non_modal_action = NON_MODAL_GO_HOME; break;
          case 53: absolute_override = true; break;
          case 54: case 55: case 56: case 57: case 58: case 59:
            int_value -= 54; // Compute coordinate system row index (0=G54,1=G55,...)
            if (int_value < N_COORDINATE_SYSTEM) {
              sys.coord_select = int_value;
            } else {
              FAIL(STATUS_UNSUPPORTED_STATEMENT);
            }
            break;
          case 80: gc.motion_mode = MOTION_MODE_CANCEL; break;
          case 90: gc.absolute_mode = true; break;
          case 91: gc.absolute_mode = false; break;
          case 92: 
            int_value = trunc(10*value); // Multiply by 10 to pick up G92.1
            switch(int_value) {
              case 920: non_modal_action = NON_MODAL_SET_COORDINATE_OFFSET; break;        
              case 921: non_modal_action = NON_MODAL_RESET_COORDINATE_OFFSET; break;
              default: FAIL(STATUS_UNSUPPORTED_STATEMENT);
            }
            break;
          case 93: gc.inverse_feed_rate_mode = true; break;
          case 94: gc.inverse_feed_rate_mode = false; break;
          default: FAIL(STATUS_UNSUPPORTED_STATEMENT);
        }
        break;        
      case 'M':
        // Set modal group values
        switch(int_value) {
          case 0: case 1: case 2: case 30: group_number = MODAL_GROUP_4; break;
          case 3: case 4: case 5: group_number = MODAL_GROUP_7; break;
        }        
        // Set 'M' commands
        switch(int_value) {
          case 0: gc.program_flow = PROGRAM_FLOW_PAUSED; break; // Program pause
          case 1: // Program pause with optional stop on
            // if (sys.opt_stop) { // TODO: Add system variable for optional stop.
            gc.program_flow = PROGRAM_FLOW_PAUSED; break; 
            // }
          case 2: case 30: gc.program_flow = PROGRAM_FLOW_COMPLETED; break; // Program end and reset 
          case 3: gc.spindle_direction = 1; break;
          case 4: gc.spindle_direction = -1; break;
          case 5: gc.spindle_direction = 0; break;
          default: FAIL(STATUS_UNSUPPORTED_STATEMENT);
        }            
        break;
    }    
    // Check for modal group multiple command violations in the current block
    if (group_number) {
      if ( bit_istrue(modal_group_words,bit(group_number)) ) {
        FAIL(STATUS_MODAL_GROUP_VIOLATION);
      } else {
        bit_true(modal_group_words,bit(group_number));
      }
      group_number = MODAL_GROUP_NONE; // Reset for next command.
    }
  } 

  // If there were any errors parsing this line, we will return right away with the bad news
  if (gc.status_code) { return(gc.status_code); }
  
  /* Pass 2: Parameters. All units converted according to current block commands. Position 
     parameters are converted and flagged to indicate a change. These can have multiple connotations
     for different commands. Each will be converted to their proper value upon execution. */
  double p = 0, r = 0;
  uint8_t l = 0;
  char_counter = 0;
  while(next_statement(&letter, &value, line, &char_counter)) {
    switch(letter) {
      case 'F': 
        if (value <= 0) { FAIL(STATUS_INVALID_COMMAND); } // Must be greater than zero
        if (gc.inverse_feed_rate_mode) {
          inverse_feed_rate = to_millimeters(value); // seconds per motion for this motion only
        } else {          
          gc.feed_rate = to_millimeters(value); // millimeters per minute
        }
        break;
      case 'I': case 'J': case 'K': offset[letter-'I'] = to_millimeters(value); break;
      case 'L': l = trunc(value); break;
      case 'P': p = value; break;                    
      case 'R': r = to_millimeters(value); break;
      case 'S': 
        if (value < 0) { FAIL(STATUS_INVALID_COMMAND); } // Cannot be negative
        gc.spindle_speed = value;
        break;
      case 'T': 
        if (value < 0) { FAIL(STATUS_INVALID_COMMAND); } // Cannot be negative
        gc.tool = trunc(value); 
        break;
      case 'X': target[X_AXIS] = to_millimeters(value); bit_true(axis_words,bit(X_AXIS)); break;
      case 'Y': target[Y_AXIS] = to_millimeters(value); bit_true(axis_words,bit(Y_AXIS)); break;
      case 'Z': target[Z_AXIS] = to_millimeters(value); bit_true(axis_words,bit(Z_AXIS)); break;
    }
  }
  
  // If there were any errors parsing this line, we will return right away with the bad news
  if (gc.status_code) { return(gc.status_code); }
  
  
  /* Execute Commands: Perform by order of execution defined in NIST RS274-NGC.v3, Table 8, pg.41.
     NOTE: Independent non-motion/settings parameters are set out of this order for code efficiency 
     and simplicity purposes, but this should not affect proper g-code execution. */
  
  //  ([M6]: Tool change execution should be executed here.)
  
  // [M3,M4,M5]: Update spindle state
  spindle_run(gc.spindle_direction, gc.spindle_speed);
  
  //  ([M7,M8,M9]: Coolant state should be executed here.)
  
  // [G4,G10,G28,G30,G92,G92.1]: Perform dwell, set coordinate system data, homing, or set axis offsets.
  // NOTE: These commands are in the same modal group, hence are mutually exclusive. G53 is in this
  // modal group and do not effect these actions.
  switch (non_modal_action) {
    case NON_MODAL_DWELL:
      if (p < 0) { // Time cannot be negative.
        FAIL(STATUS_INVALID_COMMAND); 
      } else { 
        mc_dwell(p); 
      }
      break;
    case NON_MODAL_SET_COORDINATE_DATA:
      int_value = trunc(p); // Convert p value to int.
      if (l != 2 || (int_value < 1 || int_value > N_COORDINATE_SYSTEM)) { // L2 only. P1=G54, P2=G55, ... 
        FAIL(STATUS_UNSUPPORTED_STATEMENT); 
      } else if (!axis_words) { // No axis words.
        FAIL(STATUS_INVALID_COMMAND);
      } else {
        int_value--; // Adjust p to be inline with row array index. 
        // Update axes defined only in block. Always in machine coordinates. Can change non-active system.
        uint8_t i;
        for (i=0; i<=2; i++) { // Axes indices are consistent, so loop may be used.
          if ( bit_istrue(axis_words,bit(i)) ) { sys.coord_system[int_value][i] = target[i]; }
        }
      }
      axis_words = 0; // Axis words used. Lock out from motion modes by clearing flags.
      break;
    case NON_MODAL_GO_HOME: 
      // Move to intermediate position before going home. Obeys current coordinate system and offsets 
      // and absolute and incremental modes.
      if (axis_words) {
        // Apply absolute mode coordinate offsets or incremental mode offsets.
        uint8_t i;
        for (i=0; i<=2; i++) { // Axes indices are consistent, so loop may be used.
          if ( bit_istrue(axis_words,bit(i)) ) {
            if (gc.absolute_mode) {
              target[i] += sys.coord_system[sys.coord_select][i] + sys.coord_offset[i];
            } else {
              target[i] += gc.position[i];
            }
          } else {
            target[i] = gc.position[i];
          }
        }
        mc_line(target[X_AXIS], target[Y_AXIS], target[Z_AXIS], settings.default_seek_rate, false);
      }
      mc_go_home(); 
      clear_vector(gc.position); // Assumes home is at [0,0,0]
      axis_words = 0; // Axis words used. Lock out from motion modes by clearing flags.
      break;      
    case NON_MODAL_SET_COORDINATE_OFFSET:
      if (!axis_words) { // No axis words
        FAIL(STATUS_INVALID_COMMAND);
      } else {
        // Update axes defined only in block. Offsets current system to defined value. Does not update when
        // active coordinate system is selected, but is still active unless G92.1 disables it. 
        uint8_t i;
        for (i=0; i<=2; i++) { // Axes indices are consistent, so loop may be used.
          if (bit_istrue(axis_words,bit(i)) ) {
            sys.coord_offset[i] = gc.position[i]-sys.coord_system[sys.coord_select][i]-target[i];
          }
        }
      }
      axis_words = 0; // Axis words used. Lock out from motion modes by clearing flags.
      break;
    case NON_MODAL_RESET_COORDINATE_OFFSET: 
      clear_vector(sys.coord_offset); // Disable G92 offsets by zeroing offset vector.
      break;
  }

  // [G0,G1,G2,G3,G80]: Perform motion modes. 
  // NOTE: Commands G10,G28,G30,G92 lock out and prevent axis words from use in motion modes. 
  // Enter motion modes only if there are axis words or a motion mode command word in the block.
  if ( bit_istrue(modal_group_words,bit(MODAL_GROUP_1)) || axis_words ) {

    // G1,G2,G3 require F word in inverse time mode.  
    if ( gc.inverse_feed_rate_mode ) { 
      if (inverse_feed_rate < 0 && gc.motion_mode != MOTION_MODE_CANCEL) {
        FAIL(STATUS_INVALID_COMMAND);
      }
    }
    // Absolute override G53 only valid with G0 and G1 active.
    if ( absolute_override && !(gc.motion_mode == MOTION_MODE_SEEK || gc.motion_mode == MOTION_MODE_LINEAR)) {
      FAIL(STATUS_INVALID_COMMAND);
    }
    // Report any errors.  
    if (gc.status_code) { return(gc.status_code); }

    // Convert all target position data to machine coordinates for executing motion. Apply
    // absolute mode coordinate offsets or incremental mode offsets.
    // NOTE: Tool offsets may be appended to these conversions when/if this feature is added.
    uint8_t i;
    for (i=0; i<=2; i++) { // Axes indices are consistent, so loop may be used to save flash space.
      if ( bit_istrue(axis_words,bit(i)) ) {
        if (!absolute_override) { // Do not update target in absolute override mode
          if (gc.absolute_mode) {
            target[i] += sys.coord_system[sys.coord_select][i] + sys.coord_offset[i]; // Absolute mode
          } else {
            target[i] += gc.position[i]; // Incremental mode
          }
        }
      } else {
        target[i] = gc.position[i]; // No axis word in block. Keep same axis position.
      }
    }
  
    switch (gc.motion_mode) {
      case MOTION_MODE_CANCEL: 
        if (axis_words) { FAIL(STATUS_INVALID_COMMAND); } // No axis words allowed while active.
        break;
      case MOTION_MODE_SEEK:
        if (!axis_words) { FAIL(STATUS_INVALID_COMMAND);} 
        else { mc_line(target[X_AXIS], target[Y_AXIS], target[Z_AXIS], settings.default_seek_rate, false); }
        break;
      case MOTION_MODE_LINEAR:
        if (!axis_words) { FAIL(STATUS_INVALID_COMMAND);} 
        else { mc_line(target[X_AXIS], target[Y_AXIS], target[Z_AXIS], 
          (gc.inverse_feed_rate_mode) ? inverse_feed_rate : gc.feed_rate, gc.inverse_feed_rate_mode); }
        break;
      case MOTION_MODE_CW_ARC: case MOTION_MODE_CCW_ARC:
        // Check if at least one of the axes of the selected plane has been specified. If in center 
        // format arc mode, also check for at least one of the IJK axes of the selected plane was sent.
        if ( !( bit_false(axis_words,bit(gc.plane_axis_2)) ) || 
             ( !r && !offset[gc.plane_axis_0] && !offset[gc.plane_axis_1] ) ) { 
          FAIL(STATUS_INVALID_COMMAND);
        } else {
          if (r != 0) { // Arc Radius Mode
            /* 
              We need to calculate the center of the circle that has the designated radius and passes
              through both the current position and the target position. This method calculates the following
              set of equations where [x,y] is the vector from current to target position, d == magnitude of 
              that vector, h == hypotenuse of the triangle formed by the radius of the circle, the distance to
              the center of the travel vector. A vector perpendicular to the travel vector [-y,x] is scaled to the 
              length of h [-y/d*h, x/d*h] and added to the center of the travel vector [x/2,y/2] to form the new point 
              [i,j] at [x/2-y/d*h, y/2+x/d*h] which will be the center of our arc.
              
              d^2 == x^2 + y^2
              h^2 == r^2 - (d/2)^2
              i == x/2 - y/d*h
              j == y/2 + x/d*h
              
                                                                   O <- [i,j]
                                                                -  |
                                                      r      -     |
                                                          -        |
                                                       -           | h
                                                    -              |
                                      [0,0] ->  C -----------------+--------------- T  <- [x,y]
                                                | <------ d/2 ---->|
                        
              C - Current position
              T - Target position
              O - center of circle that pass through both C and T
              d - distance from C to T
              r - designated radius
              h - distance from center of CT to O
              
              Expanding the equations:
    
              d -> sqrt(x^2 + y^2)
              h -> sqrt(4 * r^2 - x^2 - y^2)/2
              i -> (x - (y * sqrt(4 * r^2 - x^2 - y^2)) / sqrt(x^2 + y^2)) / 2 
              j -> (y + (x * sqrt(4 * r^2 - x^2 - y^2)) / sqrt(x^2 + y^2)) / 2
             
              Which can be written:
              
              i -> (x - (y * sqrt(4 * r^2 - x^2 - y^2))/sqrt(x^2 + y^2))/2
              j -> (y + (x * sqrt(4 * r^2 - x^2 - y^2))/sqrt(x^2 + y^2))/2
              
              Which we for size and speed reasons optimize to:
    
              h_x2_div_d = sqrt(4 * r^2 - x^2 - y^2)/sqrt(x^2 + y^2)
              i = (x - (y * h_x2_div_d))/2
              j = (y + (x * h_x2_div_d))/2
              
            */
            
            // Calculate the change in position along each selected axis
            double x = target[gc.plane_axis_0]-gc.position[gc.plane_axis_0];
            double y = target[gc.plane_axis_1]-gc.position[gc.plane_axis_1];
            
            clear_vector(offset);
            double h_x2_div_d = -sqrt(4 * r*r - x*x - y*y)/hypot(x,y); // == -(h * 2 / d)
            // If r is smaller than d, the arc is now traversing the complex plane beyond the reach of any
            // real CNC, and thus - for practical reasons - we will terminate promptly:
            if(isnan(h_x2_div_d)) { FAIL(STATUS_FLOATING_POINT_ERROR); return(gc.status_code); }
            // Invert the sign of h_x2_div_d if the circle is counter clockwise (see sketch below)
            if (gc.motion_mode == MOTION_MODE_CCW_ARC) { h_x2_div_d = -h_x2_div_d; }
            
            /* The counter clockwise circle lies to the left of the target direction. When offset is positive,
               the left hand circle will be generated - when it is negative the right hand circle is generated.
               
               
                                                             T  <-- Target position
                                                             
                                                             ^ 
                  Clockwise circles with this center         |          Clockwise circles with this center will have
                  will have > 180 deg of angular travel      |          < 180 deg of angular travel, which is a good thing!
                                                   \         |          /   
      center of arc when h_x2_div_d is positive ->  x <----- | -----> x <- center of arc when h_x2_div_d is negative
                                                             |
                                                             |
                                                             
                                                             C  <-- Current position                                 */
                    
    
            // Negative R is g-code-alese for "I want a circle with more than 180 degrees of travel" (go figure!), 
            // even though it is advised against ever generating such circles in a single line of g-code. By 
            // inverting the sign of h_x2_div_d the center of the circles is placed on the opposite side of the line of
            // travel and thus we get the unadvisably long arcs as prescribed.
            if (r < 0) { 
                h_x2_div_d = -h_x2_div_d; 
                r = -r; // Finished with r. Set to positive for mc_arc
            }        
            // Complete the operation by calculating the actual center of the arc
            offset[gc.plane_axis_0] = 0.5*(x-(y*h_x2_div_d));
            offset[gc.plane_axis_1] = 0.5*(y+(x*h_x2_div_d));

          } else { // Arc Center Format Offset Mode            
            r = hypot(offset[gc.plane_axis_0], offset[gc.plane_axis_1]); // Compute arc radius for mc_arc
          }
          
          // Set clockwise/counter-clockwise sign for mc_arc computations
          uint8_t isclockwise = false;
          if (gc.motion_mode == MOTION_MODE_CW_ARC) { isclockwise = true; }
    
          // Trace the arc
          mc_arc(gc.position, target, offset, gc.plane_axis_0, gc.plane_axis_1, gc.plane_axis_2,
            (gc.inverse_feed_rate_mode) ? inverse_feed_rate : gc.feed_rate, gc.inverse_feed_rate_mode,
            r, isclockwise);
        }            
        break;
    }
    
    // Report any errors.
    if (gc.status_code) { return(gc.status_code); }    
    
    // As far as the parser is concerned, the position is now == target. In reality the
    // motion control system might still be processing the action and the real tool position
    // in any intermediate location.
    memcpy(gc.position, target, sizeof(double)*3); // gc.position[] = target[];
  }
  
  // M0,M1,M2,M30: Perform non-running program flow actions. During a program pause, the buffer may 
  // refill and can only be resumed by the cycle start run-time command.
  if (gc.program_flow) {
    plan_synchronize(); // Finish all remaining buffered motions. Program paused when complete.
    sys.auto_start = false; // Disable auto cycle start.
    gc.program_flow = PROGRAM_FLOW_RUNNING; // Re-enable program flow after pause complete.
    
    // If complete, reset to reload defaults (G92.2,G54,G17,G90,G94,M48,G40,M5,M9)
    if (gc.program_flow == PROGRAM_FLOW_COMPLETED) { sys.abort = true; }
  }    
  
  return(gc.status_code);
}
Пример #21
0
/* 
 * xmpQueryInformation
 *
 * Description:
 *   QueryInformation Handler
 *
 * Arguments:
 *
 *   MiniportAdapterContext  Pointer to the adapter structure
 *   NdisRequest             Pointer to the query request
 *
 *  Return Value:
 *   
 *   NDIS_STATUS_SUCCESS
 *   NDIS_STATUS_NOT_SUPPORTED
 *   NDIS_STATUS_BUFFER_TOO_SHORT
 *
 *  IRQL: <=DISPATCH_LEVEL
 *
 *  Notes:
 */
NDIS_STATUS
xmpQueryInformation(
  IN  xmpNicCtx_t             *pNicCtx,
  IN  PNDIS_OID_REQUEST       NdisRequest
  )
{
  NDIS_STATUS                 Status = NDIS_STATUS_SUCCESS;
  NDIS_OID                    Oid;
  VOID                       *InformationBuffer;
  ULONG                       InformationBufferLength;
  ULONG                       BytesWritten;
  ULONG                       BytesNeeded;
  ULONG                       VendorDescSize;
  ULONG                       i;
  ULONG                       InfoVal = 0;
  USHORT                      InfoVal2;
  U64                         InfoVal8 = 0;
  VOID                       *pInfo = (VOID *) &InfoVal;
  ULONG                       InfoLen = sizeof(InfoVal);
  ULONG                       BytesAvailable = InfoLen;
  NDIS_HARDWARE_STATUS        HardwareStatus = NdisHardwareStatusReady;
  NDIS_MEDIUM                 Medium = XENAMP_NDIS_MEDIA_TYPE;
  NDIS_PHYSICAL_MEDIUM        PhysMedium = NdisPhysicalMediumUnspecified;
  UCHAR                       VendorDesc[] = XENAMP_VENDOR_DESC;
  ULONG                       VendorDriverVersion = XENAMP_DRIVER_VERSION;
  xge_hal_device_t           *pHalDev;
  xge_hal_pci_bar0_t         *bar0;
  NDIS_RECEIVE_SCALE_CAPABILITIES RssCapabilities = {0};
  NDIS_OFFLOAD OffloadCapabilities = {0};
  NDIS_INTERRUPT_MODERATION_PARAMETERS IntrModr = {0};


  pHalDev = XMP_NIC_GET_DEV(pNicCtx);
  bar0 = (xge_hal_pci_bar0_t *)(void *)pHalDev->bar0;

  Oid = NdisRequest->DATA.QUERY_INFORMATION.Oid;
  InformationBuffer = NdisRequest->DATA.QUERY_INFORMATION.InformationBuffer;
  InformationBufferLength = NdisRequest->DATA.QUERY_INFORMATION.InformationBufferLength;

  BytesWritten = 0;
  BytesNeeded = 0;
  XMPTRACE(XMP_DBG_REQ, ("==> xmpQueryInformation: OID=%x\n", Oid));

  switch(Oid)
  {
  case OID_GEN_SUPPORTED_LIST:
    pInfo = (PVOID) xmpNicSupportedOids;
    BytesAvailable = InfoLen = sizeof(xmpNicSupportedOids);
    break;
    
  case OID_GEN_HARDWARE_STATUS:
    pInfo = (PVOID) &HardwareStatus; /* TODO: Get from hal */
    BytesAvailable = InfoLen = sizeof(NDIS_HARDWARE_STATUS);
    break;

  case OID_GEN_MEDIA_SUPPORTED:
  case OID_GEN_MEDIA_IN_USE:
    pInfo = (PVOID) &Medium;
    BytesAvailable = InfoLen = sizeof(NDIS_MEDIUM);
    break;

  case OID_GEN_PHYSICAL_MEDIUM:
    pInfo = (PVOID) &PhysMedium;
    BytesAvailable = InfoLen = sizeof(NDIS_PHYSICAL_MEDIUM);
    break;

  case OID_GEN_CURRENT_LOOKAHEAD:
  case OID_GEN_MAXIMUM_LOOKAHEAD:
    InfoVal = (ULONG32) (pNicCtx->LookAheadSz ? 
                         pNicCtx->LookAheadSz : XMP_NIC_CURRENT_MTU(pNicCtx));
    XMPTRACE(XMP_DBG_REQ, ("xmpQueryInformation: Lookahead Sz=%d\n", InfoVal));
    break;   

  case OID_GEN_MAXIMUM_FRAME_SIZE:
    InfoVal = XMP_NIC_CURRENT_MTU(pNicCtx);
    XMPTRACE(XMP_DBG_REQ, ("xmpQueryInformation: Max Frame Sz=%d\n", InfoVal));
    break;

  case OID_GEN_MAXIMUM_TOTAL_SIZE:
  case OID_GEN_TRANSMIT_BLOCK_SIZE:
  case OID_GEN_RECEIVE_BLOCK_SIZE:
    InfoVal = pNicCtx->MaxFrameSz;
    XMPTRACE(XMP_DBG_REQ,
             ("xmpQueryInformation: Tx/Rx block/Max total Sz=%d\n", InfoVal));
    break;

  case OID_GEN_MAC_OPTIONS: 
    InfoVal = XMP_NIC_MAC_OPTIONS(pNicCtx);
    if ( pNicCtx->Flags & XMP_NIC_FLAGS_8021P )
    {
      InfoVal |= NDIS_MAC_OPTION_8021P_PRIORITY;
    }
    if ( pNicCtx->Flags & XMP_NIC_FLAGS_8021Q )
    {
      InfoVal |= NDIS_MAC_OPTION_8021Q_VLAN;
    }
    XMPTRACE(XMP_DBG_REQ,
             ("xmpQueryInformation: Mac Options=%lx: 802.1P=%s 802.1Q=%s\n",
              InfoVal,
              bit(InfoVal, NDIS_MAC_OPTION_8021P_PRIORITY) ? "YES" : "NO",
              bit(InfoVal, NDIS_MAC_OPTION_8021Q_VLAN) ? "YES" : "NO"));
    break;

  case OID_GEN_LINK_SPEED:
    InfoVal8 = XMP_NIC_MAX_SPEED(pNicCtx);
    XMPTRACE(XMP_DBG_REQ, ("xmpQueryInformation: Link speed=%ld\n", InfoVal8));
    pInfo = (PVOID) &InfoVal8;
    InfoLen = sizeof(InfoVal8);
    break;

  case OID_GEN_MEDIA_CONNECT_STATUS:
    XF_GET_SLOCK(&pNicCtx->lock);
     InfoVal =  bit(pNicCtx->State, XMP_NIC_STATE_NOLINK) ?
     NdisMediaStateDisconnected : NdisMediaStateConnected;
    pNicCtx->ReportedState = (InfoVal == NdisMediaStateConnected) ?
    MediaConnectStateConnected : MediaConnectStateDisconnected;
    XF_FREE_SLOCK(&pNicCtx->lock);
    XMPTRACE(XMP_DBG_REQ, ("xmpQueryInformation: Link Status=%s\n",
              InfoVal ==  NdisMediaStateDisconnected ? "DISCONN" : "Connect"));
    break;

  case OID_GEN_TRANSMIT_BUFFER_SPACE:
    InfoVal = XMP_NIC_GET_TX_BUF_SIZE(pNicCtx);
    XMPTRACE(XMP_DBG_REQ, ("xmpQueryInformation: Tx Buf Space=%d\n", InfoVal));
    break;

  case OID_GEN_RECEIVE_BUFFER_SPACE:
    InfoVal = XMP_NIC_GET_RX_BUF_SIZE(pNicCtx);
    XMPTRACE(XMP_DBG_REQ, ("xmpQueryInformation: Rx Buf Space=%d\n", InfoVal));
    break;

  case OID_GEN_VENDOR_DESCRIPTION:
    pInfo = VendorDesc;
    InfoLen = sizeof(VendorDesc);
    break;

  case OID_GEN_VENDOR_ID:
    InfoVal = XENAMP_VENDOR_ID;
    break;
    
  case OID_GEN_VENDOR_DRIVER_VERSION:
    InfoVal = (ULONG) VendorDriverVersion;
    break;

  case OID_GEN_DRIVER_VERSION:
    InfoVal2 = (USHORT) ((XENAMP_NDIS_MAJOR_VERSION << 8) |
                         XENAMP_NDIS_MINOR_VERSION);
    pInfo = (PVOID) &InfoVal2;
    InfoLen = sizeof(InfoVal2);
    break;

  case OID_OFFLOAD_ENCAPSULATION:

    if ( InformationBufferLength < sizeof(NDIS_OFFLOAD_ENCAPSULATION) )
    {
      BytesNeeded = sizeof(NDIS_OFFLOAD_ENCAPSULATION);
      Status = NDIS_STATUS_BUFFER_TOO_SHORT;
      break;
    }

    pInfo = (VOID *) &pNicCtx->OffloadEncapsulation;
    BytesAvailable = InfoLen = sizeof (NDIS_OFFLOAD_ENCAPSULATION);
    break;

  case OID_802_3_PERMANENT_ADDRESS:
   /* Should I store permanent address in the Nic Context too */
    pInfo =  XMP_NIC_PERMANENT_ADDRESS(pNicCtx);
    BytesAvailable = InfoLen = ETH_LENGTH_OF_ADDRESS;
    { UCHAR *pc = (UCHAR *) pInfo;
    XMPTRACE(XMP_DBG_REQ, ("xmpQueryInformation:PermAddr=%x%x%x%x%x%x\n",
                           pc[0], pc[1], pc[2], pc[3], pc[4], pc[5]));
    }
    break;

  case OID_802_3_CURRENT_ADDRESS:
    pInfo = XMP_NIC_CURRENT_ADDRESS(pNicCtx);
    BytesAvailable = InfoLen = ETH_LENGTH_OF_ADDRESS;
    { UCHAR *pc = (UCHAR *) pInfo;
    XMPTRACE(XMP_DBG_REQ, ("xmpQueryInformation:CurAddr=%x%x%x%x%x%x\n",
                           pc[0], pc[1], pc[2], pc[3], pc[4], pc[5]));
    }
    break;

  case OID_802_3_MAXIMUM_LIST_SIZE:
    InfoVal = XMP_NIC_MAX_MULTICAST_LIST_SIZE(pNicCtx);
    XMPTRACE(XMP_DBG_REQ, ("xmpQueryInformation: Max List Sz=%d\n", InfoVal));
    break;

  case OID_802_3_MULTICAST_LIST:
    pInfo  = pNicCtx->AddrList.MacAddr[XMP_HAL_MC_ADDRESS_START_OFFSET];
    BytesAvailable = InfoLen = pNicCtx->AddrList.McCnt * sizeof(xmpMacAddr_t);
    break;
    
  case OID_GEN_MAXIMUM_SEND_PACKETS:
   /* TBD: Need to correct it: I think it does not have to be fifo len, it's
    the no of packet descriptors in a single MiniportSendPackets Call i.e should
    */
    InfoVal = pNicCtx->TxFifo[0].CfgTxDCnt;
    XMPTRACE(XMP_DBG_REQ, ("xmpQueryInformation:Max Send Pkts=%d\n", InfoVal));
    break;

  case OID_GEN_XMIT_OK:
  case OID_GEN_RCV_OK:
  case OID_GEN_XMIT_ERROR:
  case OID_GEN_RCV_ERROR:
  case OID_GEN_RCV_NO_BUFFER:
  case OID_GEN_RCV_CRC_ERROR:
  case OID_GEN_TRANSMIT_QUEUE_LENGTH:
  case OID_802_3_XMIT_ONE_COLLISION:
  case OID_802_3_XMIT_MORE_COLLISIONS:
  case OID_802_3_XMIT_MAX_COLLISIONS:
  case OID_802_3_RCV_ERROR_ALIGNMENT:
  case OID_GEN_DIRECTED_FRAMES_XMIT:
  case OID_GEN_DIRECTED_FRAMES_RCV:
  case OID_GEN_MULTICAST_FRAMES_XMIT:
  case OID_GEN_MULTICAST_FRAMES_RCV:
  case OID_GEN_BROADCAST_FRAMES_XMIT:
  case OID_GEN_BROADCAST_FRAMES_RCV:
    if ( Oid == OID_GEN_RCV_OK )
      InfoVal8 = pNicCtx->RxInfo[0].Stats.RxCnt;
    else if ( Oid == OID_GEN_XMIT_OK )
      InfoVal8 = pNicCtx->TxFifo[0].Stats.TxNBLCount;
    else
      Status = xmpGetStatsCounters(pNicCtx, Oid, &InfoVal8);
    BytesNeeded = BytesAvailable = InfoLen = sizeof(InfoVal8);
    if ( Status == NDIS_STATUS_SUCCESS )
    {
      if ( InformationBufferLength < sizeof(ULONG) )
      {
        Status = NDIS_STATUS_BUFFER_TOO_SHORT;
        break;
      }
      InfoLen = MIN(InformationBufferLength, BytesAvailable);
      pInfo = &InfoVal8;
    }
    break;
  case OID_GEN_STATISTICS:
    if ( InformationBufferLength < sizeof(NDIS_STATISTICS_INFO) )
    {
      BytesNeeded = sizeof(NDIS_STATISTICS_INFO);
      Status = NDIS_STATUS_BUFFER_TOO_SHORT;
      break;
    }

    BytesWritten = sizeof(NDIS_STATISTICS_INFO);
    InfoLen = 0;                                           /* To avoid copy */
    Status = xmpGetStatsCounters(pNicCtx, Oid, (U64 *) InformationBuffer);
    break;

  case OID_GEN_RECEIVE_SCALE_CAPABILITIES:
    XMPTRACE(XMP_DBG_INFO, ("xmpQueryInformation: OID_GEN_RECEIVE_SCALE_CAPABILITIES\n"));
    if ( !(XMP_NIC_RSS_IN_CONFIG(pNicCtx)) )
    {
      Status = NDIS_STATUS_NOT_SUPPORTED;
      break;
    }

    if ( InformationBufferLength < sizeof(NDIS_RECEIVE_SCALE_CAPABILITIES) )
    {
      BytesNeeded = sizeof(NDIS_RECEIVE_SCALE_CAPABILITIES);
      Status = NDIS_STATUS_BUFFER_TOO_SHORT;
      break;
    }

    XENAMP_NDIS_OBJECT_INIT(&RssCapabilities.Header,
                            NDIS_OBJECT_TYPE_RSS_CAPABILITIES,
                            NDIS_RECEIVE_SCALE_CAPABILITIES_REVISION_1,
                            sizeof(NDIS_RECEIVE_SCALE_CAPABILITIES));
	  xmpNicInitRssCapabilities(pNicCtx,&RssCapabilities);

    pInfo = (VOID *) &RssCapabilities;
    InfoLen = sizeof (NDIS_RECEIVE_SCALE_CAPABILITIES);
    break;

  case OID_GEN_RECEIVE_SCALE_PARAMETERS:
    XMPTRACE(XMP_DBG_INFO, ("xmpQueryInformation: OID_GEN_RECEIVE_SCALE_PARAMETERS\n"));
    pInfo = (VOID *)&pNicCtx->ndisRssSet.params;
    InfoLen = pNicCtx->ndisRssSet.size;
	  break;

  case OID_GEN_INTERRUPT_MODERATION:
    XENAMP_NDIS_OBJECT_INIT(&IntrModr.Header,
                             NDIS_OBJECT_TYPE_DEFAULT,
                             NDIS_INTERRUPT_MODERATION_PARAMETERS_REVISION_1,
                             sizeof(NDIS_INTERRUPT_MODERATION_PARAMETERS));
    IntrModr.Flags = NDIS_INTERRUPT_MODERATION_CHANGE_NEEDS_RESET;
    IntrModr.InterruptModeration = NdisInterruptModerationEnabled; 
    pInfo = (PVOID) &IntrModr;
    InfoLen = sizeof(NDIS_INTERRUPT_MODERATION_PARAMETERS);
    break;

  default :
    Status = xmpDiagQueryInformation(pNicCtx, 
                                    Oid, 
                                    InformationBuffer, 
                                    InformationBufferLength,
                                    &InfoLen,
                                    &BytesNeeded);
    if(Status == NDIS_STATUS_SUCCESS)
      pInfo = (VOID *) InformationBuffer;
    break;
  }

  if ( Status == NDIS_STATUS_SUCCESS )
  {
    /*    BytesNeeded = BytesAvailable;*/
    if ( InfoLen <= InformationBufferLength )
    {
      if ( InfoLen )
      {
        BytesWritten = InfoLen;
        NdisMoveMemory(InformationBuffer, pInfo, InfoLen);
      }
    }
    else
    {
      BytesNeeded = InfoLen;
      Status = NDIS_STATUS_BUFFER_TOO_SHORT;
    }
  }

  NdisRequest->DATA.QUERY_INFORMATION.BytesWritten = BytesWritten;
  NdisRequest->DATA.QUERY_INFORMATION.BytesNeeded = BytesNeeded;
  XMPTRACE(XMP_DBG_REQ, ("<== xmpQueryInformation: Status=%x\n", Status));
  return Status;
}
Пример #22
0
/*
 * Remove an entry given a key in a Patricia trie.
 */
int pat_remove(struct ptree *n, struct ptree *head) {
	struct ptree *p, *g, *pt, *pp, *t = NULL;
	struct ptree_mask *buf, *pm;
	int i;

	if (!n || !n->p_m || !t) {
		return 0;
	}

	/*
	 * Search for the target node, while keeping track of the
	 * parent and grandparent nodes.
	 */
	g = p = t = head;

	do {
		i = t->p_b;
		g = p;
		p = t;
		t = bit(t->p_b, n->p_key) ? t->p_right : t->p_left;
	} while (i < t->p_b);

	/*
	 * For removal, we need an exact match.
	 */
	if (t->p_key != n->p_key) {
		return 0;
	}

	/*
	 * If there is only 1 mask, we can remove the entire node.
	 */
	if (t->p_mlen == 1) {
		/*
		 * Don't allow removal of the default entry.
		 */
		if (t->p_b == 0) {
			return 0;
		}

		/*
		 * Must match on the mask.
		 */
		if (t->p_m->pm_mask != n->p_m->pm_mask) {
			return 0;
		}

		/*
		 * Search for the node that points to the parent, so
		 * we can make sure it doesn't get lost.
		 */
		pp = pt = p;

		do {
			i = pt->p_b;
			pp = pt;
			pt = bit(pt->p_b, p->p_key) ? pt->p_right : pt->p_left;
		} while (i < pt->p_b);

		if (bit(pp->p_b, p->p_key)) {
			pp->p_right = t;
		} else {
			pp->p_left = t;
		}

		/*
		 * Point the grandparent to the proper node.
		 */
		if (bit(g->p_b, n->p_key))
			g->p_right = bit(p->p_b, n->p_key) ? p->p_left : p->p_right;
		else
			g->p_left = bit(p->p_b, n->p_key) ? p->p_left : p->p_right;

		/*
		 * Delete the target's data and copy in its parent's
		 * data, but not the bit value.
		 */
		if (t->p_m->pm_data) {
			free(t->p_m->pm_data);
		}

		free(t->p_m);

		if (t != p) {
			t->p_key = p->p_key;
			t->p_m = p->p_m;
			t->p_mlen = p->p_mlen;
		}

		free(p);
		return 1;
	}

	/*
	 * Multiple masks, so we need to find the one to remove.
	 * Return if we don't match on any of them.
	 */
	for (i = 0; i < t->p_mlen; i++)
		if (n->p_m->pm_mask == t->p_m[i].pm_mask) {
			break;
		}

	if (i >= t->p_mlen) {
		return 0;
	}

	/*
	 * Allocate space for a new set of masks.
	 */
	buf = (struct ptree_mask *) malloc(sizeof (struct ptree_mask) * (t->p_mlen - 1));

	for (i = 0, pm = buf; i < t->p_mlen; i++) {
		if (n->p_m->pm_mask != t->p_m[i].pm_mask) {
			bcopy(t->p_m + i, pm++, sizeof (struct ptree_mask));
		}
	}

	/*
	 * Free old masks and point to new ones.
	 */
	t->p_mlen--;
	free(t->p_m);
	t->p_m = buf;
	return 1;
}
Пример #23
0
/* 
 * Function: bits_lower
 * Purpose:
 *   Return a byte value in which bits numbered lower than 'b' are set.
 */
static __inline__ u_char
bits_lower(int b)
{
    return ((u_char)(bit(b) - 1));
}
Пример #24
0
/*
 * Patricia trie insert.
 *
 * 1) Go down to leaf.
 * 2) Determine longest prefix match with leaf node.
 * 3) Insert new internal node at appropriate location and
 *    attach new external node.
 */
struct ptree *pat_insert(struct ptree *n, struct ptree *head) {
	struct ptree *t;
	struct ptree_mask *buf, *pm;
	int i, copied;

	if (!head || !n || !n->p_m) {
		return 0;
	}

	/*
	 * Make sure the key matches the mask.
	 */
//	n->p_key &= n->p_m->pm_mask;

	/*
	 * Find closest matching leaf node.
	 */
	t = head;

	do {
		i = t->p_b;
		t = bit(t->p_b, n->p_key) ? t->p_right : t->p_left;
	} while (i < t->p_b);

	/*
	 * If the keys are the same we need to check the masks.
	 */
	if (n->p_key == t->p_key) {
		/*
		 * If we have a duplicate mask, replace the entry
		 * with the new one.
		 */
		for (i = 0; i < t->p_mlen; i++) {
			if (n->p_m->pm_mask == t->p_m[i].pm_mask) {
				t->p_m[i].pm_data = n->p_m->pm_data;
				free(n->p_m);
				free(n);
				n = 0;
				return t;
			}
		}

		/*
		 * Allocate space for a new set of masks.
		 */
		buf = (struct ptree_mask *) malloc(sizeof (struct ptree_mask) *
				(t->p_mlen + 1));
		/*
		 * Insert the new mask in the proper order from least
		 * to greatest mask.
		 */
		copied = 0;

		for (i = 0, pm = buf; i < t->p_mlen; pm++) {
			if (n->p_m->pm_mask > t->p_m[i].pm_mask) { //copy old mask element to new mask array
				bcopy(t->p_m + i, pm, sizeof (struct ptree_mask));
				i++;
			} else { //copy new node mask to new mask array
				bcopy(n->p_m, pm, sizeof (struct ptree_mask));
				n->p_m->pm_mask = 0xffffffff;
				copied = 1;
			}
		}

		if (!copied) { //new node mask is the greatest, so copy it to end of new mask array.
			bcopy(n->p_m, pm, sizeof (struct ptree_mask));
		}

		free(n->p_m);
		free(n);
		n = 0;
		t->p_mlen++;
		/*
		 * Free old masks and point to new ones.
		 */
		free(t->p_m);
		t->p_m = buf;

		return t;
	}

	/* 
	 * Find the first bit that differs.
	 */
	for (i = 1; i < 32 && bit(i, n->p_key) == bit(i, t->p_key); i++)
		;

	/*
	 * Recursive step.
	 */
	if (bit(head->p_b, n->p_key)) {
		head->p_right = insertR(head->p_right, n, i, head);
	} else {
		head->p_left = insertR(head->p_left, n, i, head);
	}

	return n;
}
Пример #25
0
static u_long
bitmap_get(u_char * map, u_long start_bit, u_long bit_count, 
	   boolean_t * ret_is_set)
{
    u_long		count;
    int			i;
    boolean_t		is_set;
    bitmap_offset_t 	start;
    bitmap_offset_t	end;

    start = bitmap_offset(start_bit);
    end = bitmap_offset(start_bit + bit_count);

    is_set = (map[start.byte] & bit(start.bit)) ? TRUE : FALSE;
    count = 0;

    if (start.byte < end.byte) {
	u_long n_bytes;

	if (start.bit) { /* try to align to a byte */
	    for (i = start.bit; i < NBBY; i++) {
		boolean_t	this_is_set;

		this_is_set = (map[start.byte] & bit(i)) ? TRUE : FALSE;
		if (this_is_set != is_set) {
		    goto done; /* found bit that was different, we're done */
		}
		count++;
	    }
	    start.bit = 0; /* made it to the next byte */
	    start.byte++;
	    if (start.byte == end.byte)
		goto end; /* no more bytes, check for any leftover bits */
	}
	/* calculate how many bytes are left in the range */
	n_bytes = end.byte - start.byte;

	/* check for 4 bytes of the same bits */
	while (n_bytes >= sizeof(u_long)) {
	    u_long * valPtr = (u_long *)(map + start.byte);
	    if ((is_set && *valPtr == ULONG_ALL_ONES) 
		|| (!is_set && *valPtr == 0)) {
		count += sizeof(*valPtr) * NBBY;
		start.byte += sizeof(*valPtr);
		n_bytes -= sizeof(*valPtr);
	    }
	    else
		break; /* bits differ */

	}
	/* check for 2 bytes of the same bits */
	if (n_bytes >= sizeof(u_short)) {
	    u_short * valPtr = (u_short *)(map + start.byte);
			
	    if ((is_set && *valPtr == USHORT_ALL_ONES) 
		|| (!is_set && (*valPtr == 0))) {
		count += sizeof(*valPtr) * NBBY;
		start.byte += sizeof(*valPtr);
		n_bytes -= sizeof(*valPtr);
	    }
	}

	/* check for 1 byte of the same bits */
	if (n_bytes) { 
	    if ((is_set && map[start.byte] == UCHAR_ALL_ONES) 
		|| (!is_set && map[start.byte] == 0)) {
		count += NBBY;
		start.byte++;
		n_bytes--;
	    }
	    /* we found bits that were different, find the first one */
	    if (n_bytes) { 
		for (i = 0; i < NBBY; i++) {
		    boolean_t	this_is_set;

		    this_is_set = (map[start.byte] & bit(i)) ? TRUE : FALSE;
		    if (this_is_set != is_set) {
			break;
		    }
		    count++;
		}
		goto done;
	    }
	}
    }

 end:
    for (i = start.bit; i < (int)end.bit; i++) {
	boolean_t this_is_set = (map[start.byte] & bit(i)) ? TRUE : FALSE;
	
	if (this_is_set != is_set) {
	    break;
	}
	count++;
    }

 done:
    *ret_is_set = is_set;
    return (count);
}
Пример #26
0
void update_aib(int pos, int val) {
  while (pos <= N) {
    aib[pos] += val;
    pos += bit(pos);
  }
}
Пример #27
0
/*
 * This function assumes that msm_gpio_dev::lock is held.
 */
static inline void set_gpio_bit(unsigned n, void __iomem *reg)
{
	writel(readl(reg) | bit(n), reg);
}
Пример #28
0
// Homes the specified cycle axes, sets the machine position, and performs a pull-off motion after
// completing. Homing is a special motion case, which involves rapid uncontrolled stops to locate
// the trigger point of the limit switches. The rapid stops are handled by a system level axis lock 
// mask, which prevents the stepper algorithm from executing step pulses. Homing motions typically 
// circumvent the processes for executing motions in normal operation.
// NOTE: Only the abort realtime command can interrupt this process.
// TODO: Move limit pin-specific calls to a general function for portability.
void limits_go_home(uint8_t cycle_mask) 
{
  if (sys.abort) { return; } // Block if system reset has been issued.

  // Initialize
  uint8_t n_cycle = (2*N_HOMING_LOCATE_CYCLE+1);
  uint8_t step_pin[N_AXIS];
  float target[N_AXIS];
  float max_travel = 0.0;
  uint8_t idx;
  for (idx=0; idx<N_AXIS; idx++) {  
    // Initialize step pin masks
    step_pin[idx] = get_step_pin_mask(idx);
    #ifdef COREXY    
      if ((idx==A_MOTOR)||(idx==B_MOTOR)) { step_pin[idx] = (get_step_pin_mask(X_AXIS)|get_step_pin_mask(Y_AXIS)); } 
    #endif



    if (bit_istrue(cycle_mask,bit(idx))) { 
      // Set target based on max_travel setting. Ensure homing switches engaged with search scalar.
      // NOTE: settings.max_travel[] is stored as a negative value.
      max_travel = max(max_travel,(-HOMING_AXIS_SEARCH_SCALAR)*settings.max_travel[idx]);
    }
  }

	#ifdef COREXY
		sys.position[A_MOTOR] = 0;
		sys.position[B_MOTOR] = 0;
		plan_sync_position();
	#endif


  // Set search mode with approach at seek rate to quickly engage the specified cycle_mask limit switches.
  bool approach = true;
  float homing_rate = settings.homing_seek_rate;

  uint8_t limit_state, axislock, n_active_axis;
  do {

    system_convert_array_steps_to_mpos(target,sys.position);

    // Initialize and declare variables needed for homing routine.
    axislock = 0;
    n_active_axis = 0;
    for (idx=0; idx<N_AXIS; idx++) {
      // Set target location for active axes and setup computation for homing rate.
      if (bit_istrue(cycle_mask,bit(idx))) {
        n_active_axis++;
		#ifndef COREXY
			sys.position[idx] = 0;
		#else
			sys.position[A_MOTOR] = 0;
			sys.position[B_MOTOR] = 0;
		#endif

        // Set target direction based on cycle mask and homing cycle approach state.
        // NOTE: This happens to compile smaller than any other implementation tried.
        if (bit_istrue(settings.homing_dir_mask,bit(idx))) {
          if (approach) { target[idx] = -max_travel; }
          else { target[idx] = max_travel; }
        } else { 
          if (approach) { target[idx] = max_travel; }
          else { target[idx] = -max_travel; }
        }        
        // Apply axislock to the step port pins active in this cycle.
        axislock |= step_pin[idx];
      }

    }
    homing_rate *= sqrt(n_active_axis); // [sqrt(N_AXIS)] Adjust so individual axes all move at homing rate.
    sys.homing_axis_lock = axislock;

    plan_sync_position(); // Sync planner position to current machine position.
    
    // Perform homing cycle. Planner buffer should be empty, as required to initiate the homing cycle.
    #ifdef USE_LINE_NUMBERS
      plan_buffer_line(target, homing_rate, false, false, HOMING_CYCLE_LINE_NUMBER); // Bypass mc_line(). Directly plan homing motion.
    #else
      plan_buffer_line(target, homing_rate, false, false); // Bypass mc_line(). Directly plan homing motion.
    #endif
    
    st_prep_buffer(); // Prep and fill segment buffer from newly planned block.
    st_wake_up(); // Initiate motion
    do {
      if (approach) {
        // Check limit state. Lock out cycle axes when they change.
        limit_state = limits_get_state();
        for (idx=0; idx<N_AXIS; idx++) {
          if (axislock & step_pin[idx]) {
            if (limit_state & (1 << idx)) {
				#ifndef COREXY
					axislock &= ~(step_pin[idx]);
				#else
					axislock &= ~(step_pin[A_MOTOR]|step_pin[B_MOTOR]);
				#endif
            }
          }
        }
        sys.homing_axis_lock = axislock;
      }

      st_prep_buffer(); // Check and prep segment buffer. NOTE: Should take no longer than 200us.

      // Exit routines: No time to run protocol_execute_realtime() in this loop.
      if (sys_rt_exec_state & (EXEC_SAFETY_DOOR | EXEC_RESET | EXEC_CYCLE_STOP)) {
        // Homing failure: Limit switches are still engaged after pull-off motion
        if ( (sys_rt_exec_state & (EXEC_SAFETY_DOOR | EXEC_RESET)) ||  // Safety door or reset issued
           (!approach && (limits_get_state() & cycle_mask)) ||  // Limit switch still engaged after pull-off motion
           ( approach && (sys_rt_exec_state & EXEC_CYCLE_STOP)) ) { // Limit switch not found during approach.
          mc_reset(); // Stop motors, if they are running.
          protocol_execute_realtime();
          return;
        } else {
          // Pull-off motion complete. Disable CYCLE_STOP from executing.
          system_clear_exec_state_flag(EXEC_CYCLE_STOP);
          break;
        } 
      }

    } while (STEP_MASK & axislock);

    st_reset(); // Immediately force kill steppers and reset step segment buffer.
    plan_reset(); // Reset planner buffer to zero planner current position and to clear previous motions.

    delay_ms(settings.homing_debounce_delay); // Delay to allow transient dynamics to dissipate.

    // Reverse direction and reset homing rate for locate cycle(s).
    approach = !approach;

    // After first cycle, homing enters locating phase. Shorten search to pull-off distance.
    if (approach) { 
      max_travel = settings.homing_pulloff*HOMING_AXIS_LOCATE_SCALAR; 
      homing_rate = settings.homing_feed_rate;
    } else {
      max_travel = settings.homing_pulloff;    
      homing_rate = settings.homing_seek_rate;
    }
    
  } while (n_cycle-- > 0);
      
  // The active cycle axes should now be homed and machine limits have been located. By 
  // default, Grbl defines machine space as all negative, as do most CNCs. Since limit switches
  // can be on either side of an axes, check and set axes machine zero appropriately. Also,
  // set up pull-off maneuver from axes limit switches that have been homed. This provides
  // some initial clearance off the switches and should also help prevent them from falsely
  // triggering when hard limits are enabled or when more than one axes shares a limit pin.
  #ifdef COREXY
    int32_t off_axis_position = 0;
  #endif
  int32_t set_axis_position;
  // Set machine positions for homed limit switches. Don't update non-homed axes.
  for (idx=0; idx<N_AXIS; idx++) {
    // NOTE: settings.max_travel[] is stored as a negative value.
    if (cycle_mask & bit(idx)) {
      #ifdef HOMING_FORCE_SET_ORIGIN
        set_axis_position = 0;
      #else 
        if ( bit_istrue(settings.homing_dir_mask,bit(idx)) ) {
          set_axis_position = lround((settings.max_travel[idx]+settings.homing_pulloff)*settings.steps_per_mm[idx]);
        } else {
          set_axis_position = lround(-settings.homing_pulloff*settings.steps_per_mm[idx]);
        }
      #endif
      
      #ifdef COREXY
        if (idx==X_AXIS) { 
          off_axis_position = (sys.position[B_MOTOR] - sys.position[A_MOTOR])/2;
          sys.position[A_MOTOR] = set_axis_position - off_axis_position;
          sys.position[B_MOTOR] = set_axis_position + off_axis_position;          
        } else if (idx==Y_AXIS) {
          off_axis_position = (sys.position[A_MOTOR] + sys.position[B_MOTOR])/2;
          sys.position[A_MOTOR] = off_axis_position - set_axis_position;
          sys.position[B_MOTOR] = off_axis_position + set_axis_position;
        } else {
          sys.position[idx] = set_axis_position;
        }        
      #else 
        sys.position[idx] = set_axis_position;
      #endif

    }
  }
  plan_sync_position(); // Sync planner position to homed machine position.
    
  // sys.state = STATE_HOMING; // Ensure system state set as homing before returning. 
}
Пример #29
0
void
doexec(struct command *t)
{
	tchar *sav;
	tchar *dp, **pv, **av;
	struct varent *v;
	bool slash;
	int hashval, hashval1, i;
	tchar *blk[2];
#ifdef TRACE
	tprintf("TRACE- doexec()\n");
#endif

	/*
	 * Glob the command name.  If this does anything, then we
	 * will execute the command only relative to ".".  One special
	 * case: if there is no PATH, then we execute only commands
	 * which start with '/'.
	 */
	dp = globone(t->t_dcom[0]);
	sav = t->t_dcom[0];
	exerr = 0; t->t_dcom[0] = dp;
	setname(dp);
	xfree(sav);
	v = adrof(S_path /* "path" */);
	if (v == 0 && dp[0] != '/') {
		pexerr();
	}
	slash = gflag;

	/*
	 * Glob the argument list, if necessary.
	 * Otherwise trim off the quote bits.
	 */
	gflag = 0; av = &t->t_dcom[1];
	tglob(av);
	if (gflag) {
		av = glob(av);
		if (av == 0)
			error("No match");
	}
	blk[0] = t->t_dcom[0];
	blk[1] = 0;
	av = blkspl(blk, av);
#ifdef VFORK
	Vav = av;
#endif
	trim(av);
	slash |= any('/', av[0]);

	xechoit(av);		/* Echo command if -x */
	/*
	 * Since all internal file descriptors are set to close on exec,
	 * we don't need to close them explicitly here.  Just reorient
	 * ourselves for error messages.
	 */
	SHIN = 0; SHOUT = 1; SHDIAG = 2; OLDSTD = 0;

	/*
	 * We must do this AFTER any possible forking (like `foo`
	 * in glob) so that this shell can still do subprocesses.
	 */
	(void) sigsetmask(0);

	/*
	 * If no path, no words in path, or a / in the filename
	 * then restrict the command search.
	 */
	if (v == 0 || v->vec[0] == 0 || slash)
		pv = justabs;
	else
		pv = v->vec;
	sav = strspl(S_SLASH /* "/" */, *av); /* / command name for postpending */
#ifdef VFORK
	Vsav = sav;
#endif
	if (havhash)
		hashval = hashname(*av);
	i = 0;
#ifdef VFORK
	hits++;
#endif
	do {
		if (!slash && pv[0][0] == '/' && havhash) {
			hashval1 = hash(hashval, i);
			if (!bit(xhash, hashval1))
				goto cont;
		}

		if (pv[0][0] == 0 || eq(pv[0], S_DOT /* "." */)) { /* don't make ./xxx */
			texec(t, *av, av);
		} else {
			dp = strspl(*pv, sav);
#ifdef VFORK
			Vdp = dp;
#endif
			texec(t, dp, av);
#ifdef VFORK
			Vdp = 0;
#endif
			xfree(dp);
		}
#ifdef VFORK
		misses++;
#endif
cont:
		pv++;
		i++;
	} while (*pv);
#ifdef VFORK
	hits--;
#endif
#ifdef VFORK
	Vsav = 0;
	Vav = 0;
#endif
	xfree(sav);
	xfree((char *)av);
	pexerr();
}
Пример #30
0
// Create tags for regridding
void AMRLevelPluto::tagCells(IntVectSet& a_tags) 
{
  CH_assert(allDefined());

  if (s_verbosity >= 3)
  {
    pout() << "AMRLevelPluto::tagCells " << m_level << endl;
  }

  // Create tags based on undivided gradient of density
  const DisjointBoxLayout& levelDomain = m_UNew.disjointBoxLayout();
  IntVectSet localTags;
  // If there is a coarser level interpolate undefined ghost cells
  if (m_hasCoarser)
  {
    const AMRLevelPluto* amrGodCoarserPtr = getCoarserLevel();

    PiecewiseLinearFillPluto pwl;

    pwl.define(levelDomain,
               amrGodCoarserPtr->m_UNew.disjointBoxLayout(),
               m_numStates,
               amrGodCoarserPtr->m_problem_domain,
               amrGodCoarserPtr->m_ref_ratio,
               m_dx,
               1);

    pwl.fillInterp(m_UNew,
                   amrGodCoarserPtr->m_UNew,
                   amrGodCoarserPtr->m_UNew,
                   1.0,
                   0,
                   0,
                   m_numStates);
  }
  m_UNew.exchange(Interval(0,m_numStates-1));

  #if GEOMETRY != CARTESIAN
   const LevelData<FArrayBox>& dV = m_levelPluto.getdV();
  #endif

  // Compute relative gradient
  DataIterator dit = levelDomain.dataIterator();
  for (dit.begin(); dit.ok(); ++dit){
    const Box& b = levelDomain[dit()];
    FArrayBox gradFab(b,1);
    FArrayBox& UFab = m_UNew[dit()];

    #if GEOMETRY != CARTESIAN
     const FArrayBox& curdV = dV[dit()];
    #else
     const FArrayBox curdV;
    #endif

    m_patchPluto->computeRefGradient(gradFab, UFab, curdV, b); 

    // Tag where gradient exceeds threshold
    BoxIterator bit(b);
    for (bit.begin(); bit.ok(); ++bit){
      const IntVect& iv = bit();
      if (gradFab(iv) >= m_refineThresh) {
        localTags |= iv;
      }
    }
  }

  localTags.grow(m_tagBufferSize);

  // Need to do this in two steps unless a IntVectSet::operator &=
  // (ProblemDomain) operator is defined
  Box localTagsBox = localTags.minBox();
  localTagsBox &= m_problem_domain;
  localTags &= localTagsBox;

  a_tags = localTags;
}