Example #1
0
        public AddressInformation(AddressingMode destinationAddressingMode, AddressingMode sourceAddressingMode, bool intraPan, ArraySegment<byte> data)
        {
            var internalOffset = 0;
            if(destinationAddressingMode != AddressingMode.None)
            {
                DestinationPan = GetValue(data, 0);
                DestinationAddress = new Address(new ArraySegment<byte>(data.Array, data.Offset + 2, destinationAddressingMode.GetBytesLength()));
                internalOffset = 2 + DestinationAddress.Bytes.Count;
            }

            if(sourceAddressingMode != AddressingMode.None)
            {
                if(intraPan)
                {
                    SourcePan = DestinationPan;
                }
                else
                {
                    SourcePan = GetValue(data, internalOffset);
                    internalOffset += 2;
                }
                SourceAddress = new Address(new ArraySegment<byte>(data.Array, data.Offset + internalOffset, sourceAddressingMode.GetBytesLength()));
            }

            Bytes = data;
        }
Example #2
0
        public CC2538RF()
        {
            rxLock = new object();
            rxQueue = new Queue<Frame>();
            txQueue = new Queue<byte>();

            shortAddress = new Address(AddressingMode.ShortAddress);
            extendedAddress = new Address(AddressingMode.ExtendedAddress);
            random = new Random();
            IRQ = new GPIO();

            srcShortEnabled = new bool[24];
            srcExtendedEnabled = new bool[12];
            matchedSourceAddresses = new bool[24];
            srcShortPendEnabled = new bool[24];
            srcExtendedPendEnabled = new bool[12];
            ffsmMemory = new uint[96];

            irqHandler = new InterruptHandler<InterruptRegister, InterruptSource>(IRQ);

            irqHandler.RegisterInterrupt(InterruptRegister.IrqFlag0, InterruptSource.StartOfFrameDelimiter, 1);
            irqHandler.RegisterInterrupt(InterruptRegister.IrqFlag0, InterruptSource.FifoP, 2);
            irqHandler.RegisterInterrupt(InterruptRegister.IrqFlag0, InterruptSource.SrcMatchDone, 3);
            irqHandler.RegisterInterrupt(InterruptRegister.IrqFlag0, InterruptSource.SrcMatchFound, 4);
            irqHandler.RegisterInterrupt(InterruptRegister.IrqFlag0, InterruptSource.FrameAccepted, 5);
            irqHandler.RegisterInterrupt(InterruptRegister.IrqFlag0, InterruptSource.RxPktDone, 6);
            irqHandler.RegisterInterrupt(InterruptRegister.IrqFlag0, InterruptSource.RxMaskZero, 7);

            irqHandler.RegisterInterrupt(InterruptRegister.IrqFlag1, InterruptSource.TxAckDone, 0);
            irqHandler.RegisterInterrupt(InterruptRegister.IrqFlag1, InterruptSource.TxDone, 1);
            irqHandler.RegisterInterrupt(InterruptRegister.IrqFlag1, InterruptSource.RfIdle, 2);
            irqHandler.RegisterInterrupt(InterruptRegister.IrqFlag1, InterruptSource.CommandStrobeProcessorManualInterrupt, 3);
            irqHandler.RegisterInterrupt(InterruptRegister.IrqFlag1, InterruptSource.CommandStrobeProcessorStop, 4);
            irqHandler.RegisterInterrupt(InterruptRegister.IrqFlag1, InterruptSource.CommandStrobeProcessorWait, 5);

            var matchedSourceIndex = new DoubleWordRegister(this);
            matchedSourceIndexField = matchedSourceIndex.DefineValueField(0, 8, FieldMode.Read | FieldMode.Write);

            var srcResMask = CreateRegistersGroup(3, this, 0, 8, 
                                valueProviderCallback: ReadSrcResMaskRegister, writeCallback: WriteSrcResMaskRegister);
            var srcExtendedAddressPendingEnabled = CreateRegistersGroup(3, this, 0, 8, 
                                valueProviderCallback: ReadSrcExtendedAddressPendingEnabledRegister, writeCallback: WriteSrcExtendedAddressPendingEnabledRegister);
            var srcShortAddressPendingEnabled = CreateRegistersGroup(3, this, 0, 8, 
                                name: "SrcShortAddressPendingEnabled", valueProviderCallback: ReadSrcShortAddressPendingEnabledRegister, writeCallback: WriteSrcShortAddressPendingEnabledRegister);
            var extAddress = CreateRegistersGroup(8, this, 0, 8, 
                                valueProviderCallback: i => extendedAddress.Bytes[i], writeCallback: (i, @new) => extendedAddress.SetByte((byte)@new, i));
            panId = CreateRegistersGroup(2, this, 0, 8);
            var shortAddressRegister = CreateRegistersGroup(2, this, 0, 8, 
                                valueProviderCallback: i => shortAddress.Bytes[i], writeCallback: (i, @new) => shortAddress.SetByte((byte)@new, i));

            var sourceExtendedAddressEnable = CreateRegistersGroup(3, this, 0, 8, 
                                valueProviderCallback: ReadSourceExtendedAddressEnableRegister, writeCallback: WriteSourceExtendedAddressEnableRegister);
            var sourceShortAddressEnable = CreateRegistersGroup(3, this, 0, 8, 
                                valueProviderCallback: ReadSourceShortAddressEnableRegister, writeCallback: WriteSourceShortAddressEnableRegister);

            var frameHandling0 = new DoubleWordRegister(this, 0x40);
            autoAck = frameHandling0.DefineFlagField(5);
            autoCrc = frameHandling0.DefineFlagField(6);
            appendDataMode = frameHandling0.DefineFlagField(7);

            var frameHandling1 = new DoubleWordRegister(this, 0x1);
            pendingOr = frameHandling1.DefineFlagField(2);

            var sourceAddressMatching = new DoubleWordRegister(this, 0x7);
            sourceAddressMatchingEnabled = sourceAddressMatching.DefineFlagField(0);
            autoPendEnabled = sourceAddressMatching.DefineFlagField(1);
            pendDataRequestOnly = sourceAddressMatching.DefineFlagField(2);

            var radioStatus0 = new DoubleWordRegister(this, 0x81).WithValueField(0, 8, FieldMode.Read);
            var radioStatus1 = new DoubleWordRegister(this, 0).WithValueField(0, 8, FieldMode.Read, valueProviderCallback: ReadRadioStatus1Register);
            var rssiValidStatus = new DoubleWordRegister(this, 0x1).WithFlag(0, FieldMode.Read);

            var interruptMask = CreateRegistersGroup(2, this, 0, 8, 
                                 valueProviderCallback: i => irqHandler.GetRegisterMask(InterruptRegisterHelper.GetMaskRegister(i)), 
                                 writeCallback: (i, @new) => { irqHandler.SetRegisterMask(InterruptRegisterHelper.GetMaskRegister(i), @new); });
            var randomData = new DoubleWordRegister(this, 0).WithValueField(0, 2, FieldMode.Read, valueProviderCallback: _ => (uint)(random.Next() & 3));

            var frameFiltering0 = new DoubleWordRegister(this, 0xD);
            frameFilterEnabled = frameFiltering0.DefineFlagField(0);
            isPanCoordinator = frameFiltering0.DefineFlagField(1);
            maxFrameVersion = frameFiltering0.DefineValueField(2, 2);

            var frameFiltering1 = new DoubleWordRegister(this, 0x78);
            acceptBeaconFrames = frameFiltering1.DefineFlagField(3);
            acceptDataFrames = frameFiltering1.DefineFlagField(4);
            acceptAckFrames = frameFiltering1.DefineFlagField(5);
            acceptMacCmdFrames = frameFiltering1.DefineFlagField(6);

            var rfData = new DoubleWordRegister(this, 0).WithValueField(0, 8,
                                valueProviderCallback: _ => DequeueData(), writeCallback: (_, @new) => { EnqueueData((byte)@new); });
            var interruptFlag = CreateRegistersGroup(2, this, 0, 8, 
                                valueProviderCallback: i => irqHandler.GetRegisterValue(InterruptRegisterHelper.GetValueRegister(i)), 
                                writeCallback: (i, @new) => { irqHandler.SetRegisterValue(InterruptRegisterHelper.GetValueRegister(i), @new); });
            var commandStrobeProcessor = new DoubleWordRegister(this, 0).WithValueField(0, 8, FieldMode.Write, writeCallback: (_, @new) => { HandleSFRInstruction(@new); });

            var addresses = new Dictionary<long, DoubleWordRegister>
            {
                { (uint)Register.RfData, rfData },
                { (uint)Register.CommandStrobeProcessor, commandStrobeProcessor },
                { (uint)Register.FrameFiltering0, frameFiltering0 },
                { (uint)Register.FrameFiltering1, frameFiltering1 },
                { (uint)Register.SourceAddressMatching, sourceAddressMatching },
                { (uint)Register.FrameHandling0, frameHandling0 },
                { (uint)Register.FrameHandling1, frameHandling1 },
                { (uint)Register.RadioStatus0, radioStatus0 },
                { (uint)Register.RadioStatus1, radioStatus1 },
                { (uint)Register.RssiValidStatus, rssiValidStatus },
                { (uint)Register.RandomData, randomData },
                { (uint)Register.SourceAddressMatchingResult, matchedSourceIndex }
            };

            RegisterGroup(addresses, (uint)Register.InterruptFlag, interruptFlag);
            RegisterGroup(addresses, (uint)Register.SourceExtendedAdressEnable, sourceExtendedAddressEnable);
            RegisterGroup(addresses, (uint)Register.SourceShortAddressEnable, sourceShortAddressEnable);
            RegisterGroup(addresses, (uint)Register.InterruptMask, interruptMask);
            RegisterGroup(addresses, (uint)Register.SourceAddressMatchingResultMask, srcResMask);
            RegisterGroup(addresses, (uint)Register.SourceExtendedAddressPendingEnabled, srcExtendedAddressPendingEnabled);
            RegisterGroup(addresses, (uint)Register.SourceShortAddressPendingEnabled, srcShortAddressPendingEnabled);
            RegisterGroup(addresses, (uint)Register.ExtendedAddress, extAddress);
            RegisterGroup(addresses, (uint)Register.PanId, panId);
            RegisterGroup(addresses, (uint)Register.ShortAddressRegister, shortAddressRegister);

            registers = new DoubleWordRegisterCollection(this, addresses);

            Reset();
        }