To configure the Impinj ItemEncode device for operation, the application must set the DeviceConfig, AntennasConfig, and either the SerializationJob or InventoryJob.
The DeviceConfig configures the primary settings of the Impinj ItemEncode device. It configures both the DeviceMode and OperationMode. The DeviceConfig object is set by the SetDeviceConfigCommand. It can only be set during the Configuration State.
Device device;
DeviceConfig deviceConfig;
deviceConfig.device_mode = DEVICE_MODE_INVENTORY;
deviceConfig.operation_mode = OPERATION_MODE_CONTINUOUS;
device.SetDeviceConfig(deviceConfig);
If the user desires to operate in a fixed frequency mode, they must configure a Region as part of the DeviceConfig. This Region contains a list of frequencies for the ItemEncode device to operate on. The configured set of frequencies must be a subset of the allowed frequencies for the regulatory region. The ItemEncode device will walk through the list of frequencies in the order that they are provided.
Note
Not all Regions support a fixed frequency list.
Device device;
DeviceConfig deviceConfig;
Region region;
region.region_id = REGULATORY_REGION_ETSI_EN_302_208_V1_2_1;
// Frequencies are provided in Hz.
region.fixed_frequency_list.add(866900);
region.fixed_frequency_list.add(865700);
device.SetDeviceConfig(deviceConfig);
The OperationResponsibility object controls which operations this specific ItemEncode device is responsible for. This is particularly important in a Pipeline System, where multiple ItemEncode devices could have the same encoding operations.
The OperationResponsibility contains several flags for the encoding responsibilities of this ItemEncode device. Most of these are simply booleans to indicate whether they should perform the operation or not. These include the PC Word, Secure Password, Access Password, Kill Password, Lock Config, and Tag Specific Feature Config. For the EPC and User Memory operations, a mask is used to control the responsibility, with each bit of the mask representing a 32 bit block of the operation. For example, if the EPC mask is set to 0xC000 with the EPC encoding operation being a 96 bit payload, this device will only encode the first 64 bits of that EPC.
DeviceConfig deviceConfig;
OperationResponsibility operationResponsibility;
// Write 96 bits of EPC if specified.
operationResponsibility.EPC_memory_mask = [E000];
// Write Access Password if specified.
operationResponsibility.access_password = true;
deviceConfig.operation_responsibility = operationResponsibility;
The OperationResponsibility contains a field for tags in view count. This represents the approximate number of tags in the field of view. This parameter is only valid in Continuous Mode. A report will be sent when a tag is removed from a list of this size. A larger number will delay reports, but allow for retries if a tag remains in the field of view.
The OperationResponsibility also configures the ItemEncode Pipeline operations. It configures which devices are downstream, how many tags are in the pipeline, and which device is the Device Of Record.
DeviceConfig deviceConfig;
OperationResponsibility operationResponsibility;
STPDevice encoderTwo("SpeedwayR-XX-XX-XX");
STPDevice encoderThree("SpeedwayR-YY-YY-YY");
STPDevice verifier("SpeedwayR-ZZ-ZZ-ZZ");
// This is the approximate number of total tags in the ItemEncode pipeline.
// It should be set to exceed the total number of tags between the first
// and last ItemEncode devices.
operationResponsibility.tag_in_pipeline_view_count = 100;
// Add the list of downstream ItemEncode devices
operationResponsibility.downstream_pipeline_devices.add(encoderTwo);
operationResponsibility.downstream_pipeline_devices.add(encoderThree);
operationResponsibility.downstream_pipeline_devices.add(verifier);
// Add the Device of Record. This tells the ItemEncode device where the
// encoding volume is maintained. If there is no Device of Record set,
// the device will assume that it is the Device of Record.
operationResponsibility.device_of_record(verifier);
deviceConfig.operation_responsibility = operationResponsibility;
The DeviceConfig object allows the application to configure the ItemEncode GPI and GPO settings. The GPIConfig object controls the polarity and the signaling mode for the GPI signals. The GPOConfig controls the polarity, signaling mode, and pulse duration of the GPO signals. The TriggerConfig must also be set to enable the use of the GPIs as Start and Stop commands.
Device device;
DeviceConfig deviceConfig;
GPIConfig gpiConfig;
GPOConfig gpoConfig;
TriggerConfig triggerConfig;
// Separate mode uses unique signals for Start/Stop.
// Combined mode uses the polarity of the GPI2 signal for Start/Stop.
gpiConfig.signaling_mode = GPIO_SIGNAL_MODE_SEPARATE;
gpiConfig.GPI2_polarity = GPIO_POLARITY_ACTIVE_HIGH;
gpiConfig.GPI3_polarity = GPIO_POLARITY_ACTIVE_HIGH;
gpoConfig.signaling_mode = GPIO_SIGNAL_MODE_SEPARATE;
gpoConfig.GPO1_polarity = GPIO_POLARITY_ACTIVE_HIGH;
gpoConfig.GPO2_polarity = GPIO_POLARITY_ACTIVE_LOW;
gpoConfig.GPO3_polarity = GPIO_POLARITY_ACTIVE_LOW;
// Pulse duration is in milliseconds.
gpoConfig.GPO_pulse_duration = 1;
// Enable Start and Stop triggers
triggerConfig.start_trigger_config = StartTriggerConfig();
triggerConfig.stop_trigger_config = StopTriggerConfig();
deviceConfig.GPI_config = gpiConfig;
deviceConfig.GPO_config = gpoConfig;
deviceConfig.trigger_config = triggerConfig;
device.SetDeviceConfig(deviceConfig);
The GPI signals can be used to trigger a Start or a Stop without sending a command over the network.
| Signal | Separate Signal Mode | Combined Signal Mode |
|---|---|---|
| GPI1 | None | None |
| GPI2 | Start | Active Start | Inactive Stop |
| GPI3 | Stop | None |
| GPI4 | None | None |
The GPO signals provide a notification as to the current state of operations on the ItemEncode device.
| Signal | Active Meaning | Inactive Meaning |
|---|---|---|
| GPO1 | Operating State | Engaged State |
| GPO2 | Operation Pass | Operation Fail (if COMBINED) |
| GPO3 | Operation Fail | N/A |
| GPO4 | Engaged State | Configuration State |
The AntennasConfig configures a list of AntennaConfig objects for the Impinj ItemEncode device to cycle through. Each AntennaConfig object contains a set of parameters with which to communicate over the air. The amount of time spent on each AntennaConfig is determined by the ItemEncode device, but can be constrained by dwell times. The AntennasConfig object is set by the SetAntennaConfigCommand. It can only be set during the Configuration State.
Device device;
AntennasConfig antennasConfig;
AntennaConfig antennaConfig;
// Set the antenna_ID according to which Speedway antenna port to use
antennaConfig.antenna_ID = 1;
// Transmit power is in cdBm. This is 18 dBm. Range is 10 to 30 dBm.
antennaConfig.transmit_power = 1800;
// There is no limit on how many AntennaConfig objects are set.
antennasConfig.antenna_config.add(antennaConfig);
device.SetAntennaConfig(antennasConfig);
Within the AntennaConfig object, there are also a few Gen2 parameters. The Gen2Mode controls data rate, modulation type (both reader-to-tag and tag-to-reader), bit encoding, pulse widths and other air protocol particulars. The Gen2Session controls which session to interact with tags on. The InventorySearchMode control which state that session should be in to interact with the ItemEncode device. For further details on how sessions work, please see the UHF Gen2 Spec.
| Mode | Sensitivity | Interference Tolerance | Data Rate |
|---|---|---|---|
| Max Throughput | Good | Poor | Best |
| Max Throughput M4 | Better | Good | Better |
| Dense Reader M4 | Better | Excellent | Good |
| Dense Reader M8 | Best | Excellent | Poor |
| Max Miller | Better | Good | Good |
| Hybrid | Good | Good | Better |
Warning
Not all Gen2 modes available in all Regions.
| Mode | Description |
|---|---|
| Dual Target | This mode inventories all tags in the A state for the given session and moves them to B. It then immediately inventories all tags in the B state and moves them back to A. It then starts over again. |
| Single Target A->B | This mode inventories all tags in the A state for the given session and moves them to B. |
| Single Target B->A | This mode inventories all tags in the B state for the given session and moves them to A. |
Device device;
AntennasConfig antennasConfig;
AntennaConfig antennaConfig;
// Set the antenna_ID according to which Speedway antenna port to use
antennaConfig.antenna_ID = 1;
// Maximize data rate
antennaConfig.gen2_mode = GEN2_MODE_MAX_THROUGHPUT;
// Find all tags that are in the A state in Session 2 and move them to B
antennaConfig.gen2_session = GEN2_SESSION_2;
antennaConfig.inventory_search_mode = INVENTORY_SEARCH_MODE_SINGLE_TARGET_A_TO_B;
antennasConfig.antenna_config.add(antennaConfig);
device.SetAntennaConfig(antennasConfig);
To improve efficiency, the AntennaConfig can also take a tag population estimate parameter. This is an estimate of how many tags that this antenna should see. The user can also enable adaptive tag population estimates, which will automatically adapt the tag population estimate based on how many tags were seen the last time that AntennaConfig was used. This is useful when the size of the tag population is not static.
Device device;
AntennasConfig antennasConfig;
AntennaConfig antennaConfig;
// Set the antenna_ID according to which Speedway antenna port to use
antennaConfig.antenna_ID = 1;
// Maximize data rate
antennaConfig.gen2_mode = GEN2_MODE_MAX_THROUGHPUT;
// Start with an initial tag population of 8, but let it adapt over time.
antennaConfig.tag_population_estimate = 8;
antennaConfig.enable_adaptive_tag_population_estimate = true;
antennasConfig.antenna_config.add(antennaConfig);
device.SetAntennaConfig(antennasConfig);
The SerializationJob configures what the tag should be encoded with. It is used in Encode, Verify Tag Chip Basic, and Verify Tag Chip Data modes. It can be set using the AddSerializationJobCommand.
Device device;
SerializationJob job;
job.job_id = 1;
job.job_type = SERIALIZATION_JOB_TYPE_STATIC;
job.EPC_memory = EPCMemory();
device.AddSerializationJob(job);
The SerializationJob is used to set the Static encoding operations.
Device device;
SerializationJob job;
// EPC encoding operations
job.EPC_Memory = EPCMemory();
// Data to write to user memory data bank
job.user_memory = UserMemory();
// If tag has it's access password already set, set it here to open the tag
job.secure_password = Password();
// Data to write to the access password field
job.access_password = Password();
// Data to write to the kill password field
job.kill_password = Password();
// Payload for the Lock command
job.lock_config = LockConfig();
device.AddSerializationJob(job);
The SerializationJob can also be used to set an initial TID Table or Ordered List.
Device device;
SerializationJob job;
job.job_type = SERIALIZATION_JOB_TYPE_TID_TABLE;
// Set the max TID table size
job.TID_table_size = 100;
// Add a couple TID table entries.
job.tid_table_entries.add(TIDTableEntry());
job.tid_table_entries.add(TIDTableEntry());
job.AddSerializationJob(job);
Device device;
SerializationJob job;
job.job_type = SERIALIZATION_JOB_TYPE_ORDERED_LIST;
// Add a couple Ordered List Entries
job.ordered_list_entries.add(OrderedListEntry());
job.ordered_list_entries.add(OrderedListEntry());
job.AddSerializationJob(job);
If there is a need to limit encoding operation to a specific TID or EPC pattern, a Filter can be used to ensure that ItemEncode is only operating on tags that match that pattern. This can be accomplished by setting the SerializationJobFilters. If any filter is set, then a tag must match at least one filter for encoding operations to proceed. Else, a TagOperationResult of TAG_OPERATION_RESULT_FAIL_FILTER_NO_MATCH will be reported.
Device device;
SerializationJob job;
Filter tidFilter;
Filter epcFilter;
// Match the second word to 1160
tidFilter.data = [E2801160];
tidFilter.mask = [0000FFFF];
tidFilter.word_offset = 0;
// Match the third word (zero-based) to BEEF
epcFilter.data = [BEEF];
epcFilter.mask = [FFFF];
epcFilter.word_offset = 2;
// Add the filters to the SerializationJob
job.filters.tid_filters.add(tidFilter);
job.filters.epc_filters.add(epcFilter);
job.AddSerializationJob(job);