mercury-api-0.1.0.0: cbits/api/tm_reader.h
/* ex: set tabstop=2 shiftwidth=2 expandtab cindent: */
#ifndef _TM_READER_H
#define _TM_READER_H
/**
* @file tm_reader.h
* @brief Mercury API Reader Interface
* @author Brian Fiegel
* @date 4/18/2009
*/
/*
* Copyright (c) 2009 ThingMagic, Inc.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
/* Due to incompatibilities between winsock.h and winsock2.h (plus interactions
* with windows.h) you're in for a storm of "redefinition" errors if you don't
* include winsock2.h first.
*
* This is surprisingly hard, because lots of other headers include winsock.h
* themselves. So include winsock2.h as early as possible.
*/
#if defined(WIN32) || defined(WINCE)
#include <winsock2.h>
#endif
#include "tm_config.h"
/**
* TMR_ENABLE_JNI_SERIAL_READER_ONLY is used for building JNI project, and is defined from
* Makefile.jni
**/
#if !defined(TMR_ENABLE_SERIAL_READER_ONLY) && !defined(TMR_ENABLE_JNI_SERIAL_READER_ONLY) && defined(TMR_ENABLE_LLRP_TRANSPORT)
#define TMR_ENABLE_LLRP_READER
#endif
#ifdef TMR_ENABLE_BACKGROUND_READS
#include <pthread.h>
#include <semaphore.h>
#endif
typedef struct TMR_Reader TMR_Reader;
#include "tmr_types.h"
#include "tmr_status.h"
#include "tmr_gpio.h"
#include "tmr_params.h"
#include "tmr_read_plan.h"
#include "tmr_tag_auth.h"
#include "tmr_tag_data.h"
#include "tmr_tag_lock_action.h"
#include "tmr_tag_protocol.h"
#include "tmr_tagop.h"
#include "tmr_serial_reader.h"
#ifdef TMR_ENABLE_LLRP_READER
#include "tmr_llrp_reader.h"
#endif
#ifdef __cplusplus
extern "C" {
#endif
#ifndef DOXYGEN_IGNORE
typedef TMR_Status (*TMR_TransportNativeInit)(TMR_SR_SerialTransport *transport, TMR_SR_SerialPortNativeContext *context,
const char *device);
typedef struct TMR_readParams
{
#if defined(TMR_ENABLE_BACKGROUND_READS)|| defined(SINGLE_THREAD_ASYNC_READ)
uint32_t asyncOnTime;
uint32_t asyncOffTime;
#endif
TMR_ReadPlan defaultReadPlan;
TMR_ReadPlan *readPlan;
} TMR_readParams;
typedef struct TMR_tagOpParams
{
uint8_t antenna;
TMR_TagProtocol protocol;
}TMR_tagOpParams;
typedef enum TMR_ReaderType
{
TMR_READER_TYPE_INVALID,
TMR_READER_TYPE_RQL,
TMR_READER_TYPE_SERIAL,
TMR_READER_TYPE_LLRP,
} TMR_ReaderType;
typedef enum TMR_ReadState
{
TMR_READ_STATE_IDLE,
TMR_READ_STATE_STARTING,
TMR_READ_STATE_STARTED,
TMR_READ_STATE_ACTIVE,
TMR_READ_STATE_DONE,
} TMR_ReadState;
#endif /* DOXYGEN_IGNORE */
/**
* Reader Stats Flag Enum
*/
typedef enum TMR_Reader_StatsFlag
{
TMR_READER_STATS_FLAG_NONE = 0x00,
/** Total time the port has been transmitting, in milliseconds. Resettable */
TMR_READER_STATS_FLAG_RF_ON_TIME = (1 << 0),
/** Noise floor with the TX on for the antennas were last configured for searching */
TMR_READER_STATS_FLAG_NOISE_FLOOR_SEARCH_RX_TX_WITH_TX_ON = (1 << 6),
/** Current frequency in units of Khz */
TMR_READER_STATS_FLAG_FREQUENCY = (1 << 7),
/** Current temperature of the device in units of Celsius */
TMR_READER_STATS_FLAG_TEMPERATURE = (1 << 8),
/** Current antenna */
TMR_READER_STATS_FLAG_ANTENNA_PORTS = (1 << 9),
/** Current protocol */
TMR_READER_STATS_FLAG_PROTOCOL = (1 << 10),
/** Current connected antennas */
TMR_READER_STATS_FLAG_CONNECTED_ANTENNAS = (1 << 11),
/* ALL */
TMR_READER_STATS_FLAG_ALL = (TMR_READER_STATS_FLAG_RF_ON_TIME |
TMR_READER_STATS_FLAG_NOISE_FLOOR_SEARCH_RX_TX_WITH_TX_ON |
TMR_READER_STATS_FLAG_TEMPERATURE |
TMR_READER_STATS_FLAG_PROTOCOL |
TMR_READER_STATS_FLAG_ANTENNA_PORTS |
TMR_READER_STATS_FLAG_FREQUENCY |
TMR_READER_STATS_FLAG_CONNECTED_ANTENNAS),
}TMR_Reader_StatsFlag;
/**
* Per Antenna stats
*/
typedef struct TMR_StatsPerAntennaValues
{
/** Antenna number */
uint8_t antenna;
/** Current RF on time (since start of search) (milliseconds) */
uint32_t rfOnTime;
/** Noise Floor (TX on, all connected antennas) (dBm) */
int8_t noiseFloor;
} TMR_StatsPerAntennaValues;
/**
* Object to hold the per antenna stats
*/
typedef struct TMR_StatsPerAntennaValuesList
{
TMR_StatsPerAntennaValues *list;
uint16_t max;
uint16_t len;
} TMR_StatsPerAntennaValuesList;
/**
* This object is returned from TMR_cmdGetReaderStats
*/
typedef struct TMR_Reader_StatsValues
{
TMR_Reader_StatsFlag valid;
/** Current temperature (degrees C) */
int8_t temperature;
/** Current tag protocol */
TMR_TagProtocol protocol;
/** Current antenna */
uint16_t antenna;
/** Current RF carrier frequency (KHZ) */
uint32_t frequency;
/** Current connected antennas */
TMR_uint8List connectedAntennas;
uint8_t _connectedAntennasStorage[TMR_SR_MAX_ANTENNA_PORTS];
/** Per-antenna values */
TMR_StatsPerAntennaValuesList perAntenna;
TMR_StatsPerAntennaValues _perAntStorage[TMR_SR_MAX_ANTENNA_PORTS];
}TMR_Reader_StatsValues;
/** Type of functions to be registered as read callbacks */
typedef void (*TMR_ReadListener)(TMR_Reader *reader, const TMR_TagReadData *t,
void *cookie);
/**
* User-allocated structure containing the callback pointer and the
* value to pass to that callback.
*/
typedef struct TMR_ReadListenerBlock
{
/** Pointer to callback function */
TMR_ReadListener listener;
/** Value to pass to callback function */
void *cookie;
/** @private */
struct TMR_ReadListenerBlock *next;
} TMR_ReadListenerBlock;
/** Type of functions to be registered as tagauth request callbacks
* @param reader Reader object
* @param trd TagReadData object
* @param cookie Arbitrary data structure to be passed to callback
* @param auth [OUTPUT] Tag authentication value to initialize based on inputs
*/
typedef void (*TMR_AuthReqListener)(TMR_Reader *reader, const TMR_TagReadData *trd,
void *cookie, TMR_TagAuthentication *auth);
/**
* User-allocated structure containing the callback pointer and the
* value to pass to that callback.
*/
typedef struct TMR_AuthReqListenerBlock
{
/** Pointer to callback function */
TMR_AuthReqListener listener;
/** Value to pass to callback function */
void *cookie;
/** @private */
struct TMR_AuthReqListenerBlock *next;
} TMR_AuthReqListenerBlock;
/** Type of functions to be registered as read error callbacks */
typedef void (*TMR_ReadExceptionListener)(TMR_Reader *reader, TMR_Status error, void *cookie);
/**
* User-allocated structure containing the callback pointer and the
* value to pass to that callback.
*/
typedef struct TMR_ReadExceptionListenerBlock
{
/** Pointer to callback function */
TMR_ReadExceptionListener listener;
/** Value to pass to callback function */
void *cookie;
/** @private */
struct TMR_ReadExceptionListenerBlock *next;
} TMR_ReadExceptionListenerBlock;
/** Type of functions to be registered as transport callbacks */
typedef void (*TMR_TransportListener) (bool tx, uint32_t dataLen,
const uint8_t data[], uint32_t timeout,
void *cookie);
/**
* User-allocated structure containing the callback pointer and the
* value to pass to that callback.
*/
typedef struct TMR_TransportListenerBlock
{
/** Pointer to callback function */
TMR_TransportListener listener;
/** Value to pass to callback function */
void *cookie;
/** @private */
struct TMR_TransportListenerBlock *next;
} TMR_TransportListenerBlock;
/** Type of functions to be registered as Status read callbacks */
typedef void (*TMR_StatsListener)(TMR_Reader *reader, const TMR_Reader_StatsValues* value,
void *cookie);
typedef void (*TMR_StatusListener)(TMR_Reader *reader, const TMR_SR_StatusReport report[],
void *cookie);
/**
* User-allocated structure containing the callback pointer and the
* value to pass to that callback.
*/
typedef struct TMR_StatsListenerBlock
{
/** Pointer to callback function */
TMR_StatsListener listener;
/** Value to pass to callback function */
void *cookie;
/** @private */
struct TMR_StatsListenerBlock *next;
} TMR_StatsListenerBlock;
/**
* User-allocated structure containing the callback pointer and the
* value to pass to that callback.
*/
typedef struct TMR_StatusListenerBlock
{
/** Pointer to callback function */
TMR_StatusListener listener;
/** Value to pass to callback function */
void *cookie;
/** @private */
struct TMR_StatusListenerBlock *next;
} TMR_StatusListenerBlock;
/**
* Private: should not be used by user level application.
*/
typedef struct TMR_Queue_tagReads
{
union
{
/* Buffer to hold serial message response */
uint8_t *sMsg;
#ifdef TMR_ENABLE_LLRP_READER
/* Buffer to hold LLRP message response */
LLRP_tSMessage *lMsg;
#endif
} tagEntry;
uint8_t bufPointer;
/* Object to hold tag results */
TMR_TagReadData trd;
bool isStatusResponse;
struct TMR_Queue_tagReads *next;
}TMR_Queue_tagReads;
typedef TMR_SR_GEN2_QType TMR_GEN2_QType;
typedef TMR_SR_GEN2_QStatic TMR_GEN2_QStatic;
typedef TMR_SR_GEN2_Q TMR_GEN2_Q;
/**
* @defgroup reader Reader
*
* TMR_Reader encapsulates a connection to a ThingMagic RFID reader
* device and provides an interface to perform RFID operations such as
* reading tags and writing tag IDs.
*
* Reads can be done on demand, with the TMR_read() function, or
* continuously in the background with the TMR_startReading()
* function. Background reads notify registered listeners of tags
* that are read.
*
* Operations which take an argument for a tag to operate on may
* optionally be passed a @c NULL argument. This lets the reader choose
* what tag to use, but may not work if multiple tags are
* present. This use is recommended only when exactly one tag is known
* to be in range.
*/
/**
* @ingroup reader
* @struct TMR_Reader
*
* The structure that represents a RFID reader. The user should
* allocate a TMR_Reader structure and initialize it with
* TMR_create().
*/
struct TMR_Reader
{
/** @privatesection */
enum TMR_ReaderType readerType;
bool connected;
TMR_TransportListenerBlock *transportListeners;
TMR_readParams readParams;
TMR_tagOpParams tagOpParams;
char uri[TMR_MAX_READER_NAME_LENGTH];
bool continuousReading;
bool trueAsyncflag;
bool searchStatus;
/* Statistics response indicator */
bool isStatusResponse;
/* Option for Fast Search */
bool fastSearch;
/* Option for Trigger Read */
bool triggerRead;
/* Option for Duty cycle*/
bool dutyCycle;
/* Option for stop N tag trigger */
bool isStopNTags;
/* Param wait indicator for Reader and protocol param control during continuous read */
bool paramWait;
/* Param response for Reader and protocol param control during continuous read */
uint8_t paramMessage[256];
/* True Continuous Read Start indicator */
bool hasContinuousReadStarted;
/* Total tag count for sto N trigger */
uint32_t numberOfTagsToRead;
/* Does ResetStats feature work on this reader?
* Unknown: NULL == pSupportsResetStats
* Yes: (NULL != pSupportsResetStats) && (true == *pSupportsResetStats)
* No: (NULL != pSupportsResetStats) && (false == *pSupportsResetStats)
*/
bool* pSupportsResetStats/* = NULL*/;
bool _storeSupportsResetStats;
/* the option to request for background thread cancel */
bool backgroundThreadCancel;
union
{
TMR_SR_SerialReader serialReader;
/*
*TMR_RQL_RqlReader rqlReader;
*/
#ifdef TMR_ENABLE_LLRP_READER
TMR_LLRP_LlrpReader llrpReader;
#endif
}u;
#ifdef TMR_ENABLE_BACKGROUND_READS
bool backgroundSetup, backgroundEnabled, backgroundRunning;
bool parserSetup, parserEnabled, parserRunning;
#endif
bool finishedReading;
#ifdef TMR_ENABLE_BACKGROUND_READS
enum TMR_ReadState readState;
unsigned int queue_depth;
sem_t queue_slots, queue_length;
pthread_mutex_t queue_lock;
pthread_mutex_t backgroundLock;
pthread_mutex_t parserLock;
pthread_mutex_t listenerLock;
pthread_cond_t backgroundCond;
pthread_cond_t parserCond;
pthread_cond_t readCond;
pthread_t backgroundReader;
pthread_t backgroundParser;
pthread_t autonomousBackgroundReader;
TMR_AuthReqListenerBlock *authReqListeners;
#endif
TMR_ReadListenerBlock *readListeners;
TMR_ReadExceptionListenerBlock *readExceptionListeners;
TMR_StatsListenerBlock *statsListeners;
#ifdef TMR_ENABLE_BACKGROUND_READS
TMR_StatusListenerBlock *statusListeners;
TMR_Queue_tagReads *tagQueueTail;
TMR_Queue_tagReads *tagQueueHead;
#endif
TMR_Reader_StatsFlag statsFlag;
TMR_SR_StatusType streamStats;
TMR_TRD_MetadataFlag userMetadataFlag;
uint8_t portmask;
/* Level 1 */
#ifndef TMR_ENABLE_SERIAL_READER_ONLY
TMR_Status (*connect)(struct TMR_Reader *reader);
TMR_Status (*destroy)(struct TMR_Reader *reader);
TMR_Status (*read)(struct TMR_Reader *reader, uint32_t timeoutMs, int32_t *tagCount);
TMR_Status (*hasMoreTags)(struct TMR_Reader *reader);
TMR_Status (*getNextTag)(struct TMR_Reader *reader, TMR_TagReadData *read);
TMR_Status (*writeTag)(struct TMR_Reader *reader, const TMR_TagFilter *filter, const TMR_TagData *data);
#endif /* TMR_ENABLE_SERIAL_READER_ONLY */
TMR_Status (*paramGet)(struct TMR_Reader *reader, TMR_Param key, void *value);
TMR_Status (*paramSet)(struct TMR_Reader *reader, TMR_Param key, const void *value);
/* Level 2 */
#ifndef TMR_ENABLE_SERIAL_READER_ONLY
TMR_Status (*killTag)(struct TMR_Reader *reader, const TMR_TagFilter *filter, const TMR_TagAuthentication *auth);
TMR_Status (*lockTag)(struct TMR_Reader *reader, const TMR_TagFilter *filter, TMR_TagLockAction *action);
TMR_Status (*executeTagOp)(struct TMR_Reader *reader, TMR_TagOp *tagop, TMR_TagFilter *filter, TMR_uint8List *data);
TMR_Status (*readTagMemBytes)(struct TMR_Reader *reader, const TMR_TagFilter *filter,
uint32_t bank, uint32_t address,
uint16_t count, uint8_t data[]);
TMR_Status (*readTagMemWords)(struct TMR_Reader *reader, const TMR_TagFilter *filter,
uint32_t bank, uint32_t address,
uint16_t count, uint16_t *data);
TMR_Status (*writeTagMemBytes)(struct TMR_Reader *reader, const TMR_TagFilter *filter,
uint32_t bank, uint32_t address,
uint16_t count, const uint8_t data[]);
TMR_Status (*writeTagMemWords)(struct TMR_Reader *reader, const TMR_TagFilter *filter,
uint32_t bank, uint32_t address,
uint16_t count, const uint16_t data[]);
TMR_Status (*gpoSet)(struct TMR_Reader *reader, uint8_t count, const TMR_GpioPin state[]);
TMR_Status (*gpiGet)(struct TMR_Reader *reader, uint8_t *count, TMR_GpioPin state[]);
TMR_Status (*firmwareLoad)(TMR_Reader *reader, void *cookie, TMR_FirmwareDataProvider provider);
TMR_Status (*modifyFlash) (TMR_Reader *reader, uint8_t sector, uint32_t address, uint32_t password,
uint8_t length, const uint8_t data[], uint32_t offset);
TMR_Status (*reboot) (TMR_Reader *reader);
#endif /* TMR_ENABLE_SERIAL_READER_ONLY */
/* Level 3 */
#ifdef TMR_ENABLE_BACKGROUND_READS
TMR_Status (*cmdAutonomousReading)(struct TMR_Reader *reader, TMR_TagReadData *trd, TMR_Reader_StatsValues *stats);
#endif
TMR_Status (*cmdStopReading)(struct TMR_Reader *reader);
};
/**
* @ingroup reader
* The TMR_Reader struct being initialized should be preallocated by
* the user. No memory is allocated during the initialization
* process, and the reader is not contacted at this point.
*
* @param reader The TMR_Reader structure to initialize
* @param deviceUri an identifier for the reader to connect to, with
* a URI syntax. The scheme can be \c eapi for the embedded
* module protocol, \c rql for the request query language, or
* \c tmr to guess. The remainder of the URI identifies the
* stream that the protocol will be spoken over, either a local host
* serial port device or a TCP network port.
* Example URIs are:
* - tmr://192.168.10.8/ - Reader at TCP/IP address 192.168.10.8, RQL assumed
* - rql://192.168.10.8/ - RQL reader at TCP/IP address 192.168.10.8
* - tmr:///dev/ttyS1 - reader on serial port /dev/ttyS1, EAPI (serial) assumed
* - eapi:///COM2 - EAPI (serial) reader on serial port COM2
* - llrp+eapi://192.168.10.8 - EAPI tunneled over LLRP to a reader at
* TCP/IP address 192.168.10.8
*
* @test Call with valid URI should not fail.
* @test Call with invalid URI should fail.
*/
TMR_Status TMR_create(TMR_Reader *reader, const char* deviceUri);
/**
* @ingroup reader
*
* This function is a version of TMR_create() that dynamically
* allocates the TMR_Reader structure and stores the pointer in
* *reader.
*
* @param[out] readerPointer Pointer to the TMR_Reader* in which to place the
* pointer to the newly allocated reader structure.
@ @param deviceUri As described in TMR_create().
*
* @test Call with valid URI should not fail.
* @test Call with invalid URI should fail.
* @test Multiple calls with different URIs should return distinct objects.
*/
TMR_Status TMR_create_alloc(TMR_Reader **readerPointer, const char* deviceUri);
/**
* @ingroup reader
* Establishes the connection to the reader at the URI specified in
* the TMR_create() call. The existence of a reader at the address is
* verified and the reader is brought into a state appropriate for
* performing RF operations.
*
* @param reader The reader to connect
*
*
* @test Connecting to existing reader should succeed.
* @test Connecting to nonexisting reader should fail.
*/
TMR_Status TMR_connect(struct TMR_Reader *reader);
/**
* @ingroup reader
* Closes the connection to the reader and releases any resources
* that have been consumed by the reader structure.
*
* @param reader The reader to shut down.
*
* @test Destroying existing connected reader should succed.
* @test Destroying existing unconnected reader should succeed.
* @test Destroying already-destroyed reader should fail.
* @test Destroying reader allocated by TMR_create_alloc() should
* free the allocated memory.
*/
TMR_Status TMR_destroy(TMR_Reader *reader);
/**
* @ingroup reader
* Search for tags for a fixed duration. Once this returns, the tags
* are retrieved by calling TMR_getNextTag() until TMR_hasMoreTags()
* returns false.
*
* @param reader The reader being operated on
* @param timeoutMs The number of milliseconds to search for tags
* @param[out] tagCount The number of tags read, or -1 if the number
* is unknown. If NULL, no value will be stored.
*
* @test Call should fail if reader is not connected.
* @test If call is successful as per TMR_Error, *tagCount should be
* modified and contain a positive value.
*/
TMR_Status TMR_read(TMR_Reader *reader, uint32_t timeoutMs, int32_t *tagCount);
/**
* @ingroup reader
* @retval TMR_SUCCESS if there are more tags to be retrieved from the most recent TMR_read() operation.
* @retval TMR_ERROR_NO_TAGS if no more tags are available for retrieval.
* @retval Other TMR_ERRORs when appropriate.
*
* @param reader The reader being operated on
*
* @test Call should return false before a read() call.
* @test Call should return false after a read() call that set
* *tagCount to zero.
* @test Call should return true after a read() call that set
* *tagCount to a nonzero value.
* @test Call should return true through exactly as many getNextTag()
* calls as specified by *tagCount.
*/
TMR_Status TMR_hasMoreTags(TMR_Reader *reader);
/**
* @ingroup reader
* Fetches the next tag from the last TMR_read() operation.
*
* @param reader The reader being operated on
* @param[out] tagData The TMR_TagReadData structure to fill.
*
* @test Call should fail before a read() call.
* @test Call should fail after a read() call that set *tagCount to
* zero.
* @test Call should fill in a tag after a read() call that set
* *tagCount to a nonzero value.
* @test Call should succeed exactly as many times as specified by
* *tagCount.
*/
TMR_Status TMR_getNextTag(TMR_Reader *reader, TMR_TagReadData *tagData);
/**
* @ingroup reader
* This method provides the direct execution of TagOp commands
* Reader operates on the first tag found, with applicable tag filtering
* Reader stops and the call returns immediately after finding one tag
* and operating on it, unless the command timeout expires first
* The operation is performed on the antenna specified in
* /reader/tagop/antenna parameter
* /reader/tagop/protocol specifies the protocol to be used
*
* @param reader The reader being operated on
* @param tagop Pointer to the TMR_TagOp which needs to be executed
* @param filter Tag Filter to be used
* @param[out] data Data returned as a result of tag operation
*/
TMR_Status TMR_executeTagOp(struct TMR_Reader *reader, TMR_TagOp *tagop, TMR_TagFilter *filter, TMR_uint8List *data);
/**
* @ingroup reader
* Wrapper routine that searches for tags, allocates space for the
* results, and returns the results in a single array.
*
* @param reader The reader being operated on
* @param timeoutMs The number of milliseconds to search for tags
* @param[out] tagCount The number of tags found and the size of the allocated array.
* @param[out] result The array of tag read data.
*
* @test Call should fail if reader is not connected.
* @test If call is successful as per TMR_Error, *tagCount should be
* modified and contain a positive value, and *result should be
* modified and contain the corresponding number of tag read values.
*
* Out param "result" should be freed after using it.
*/
TMR_Status TMR_readIntoArray(struct TMR_Reader *reader, uint32_t timeoutMs, int32_t *tagCount, TMR_TagReadData *result[]);
/**
* @deprecated This method is deprecated
*
* Write a new EPC to an existing tag.
*
* The @c /reader/tagop/antenna parameter controls which antenna will
* be used for the write operation. The @c /reader/tagop/protocol
* parameter controls which protocol will be used.
*
* @param reader The reader being operated on
* @param target The existing tag to write.
* @param data The EPC to write to the tag
* @note target is not supported on serial or Astra readers and only
* TagData filters are supported on other fixed readers.
*
* @return TMR_ERROR_NO_TAG_FOUND if no tag matching the filter could be found.
*
* @test Call should fail if reader is not connected.
* @test Upon success, a subsequent TMR_read() should find the new tag ID.
*/
TMR_Status TMR_writeTag(TMR_Reader *reader, const TMR_TagFilter *target, TMR_TagData *data);
/**
* @deprecated This method is deprecated
*
* Sends a kill command to a tag.
*
* @param reader The reader being operated on.
* @param target The tag to kill, or @c NULL to kill the first tag seen.
* @param auth The authentication needed to kill the tag.
*
* @return TMR_ERROR_NO_TAG_FOUND if no tag matching the filter could be found.
*/
TMR_Status TMR_killTag(TMR_Reader *reader, TMR_TagFilter *target, TMR_TagAuthentication *auth);
/**
* @deprecated This method is deprecated
*
* Sends a lock command to a tag.
*
* @param reader The reader being operated on.
* @param target The tag to kill, or @c NULL to kill the first tag seen.
* @param action The locking action to apply.
*
* @return TMR_ERROR_NO_TAG_FOUND if no tag matching the filter could be found.
*/
TMR_Status TMR_lockTag(TMR_Reader *reader, TMR_TagFilter *target, TMR_TagLockAction *action);
/**
* @ingroup reader
* Read 8-bit bytes from the memory bank of a tag.
*
* @param reader The reader being operated on.
* @param target The tag to read from, or @c NULL.
* @param bank The tag memory bank to read from.
* @param byteAddress The byte address to start reading at.
* @param byteCount The number of bytes to read
* @param[out] data The read data.
*/
TMR_Status TMR_readTagMemBytes(TMR_Reader *reader, TMR_TagFilter *target,
uint32_t bank, uint32_t byteAddress,
uint16_t byteCount, uint8_t data[]);
/**
* @ingroup reader
* Read 16-bit words from the memory bank of a tag.
*
* @param reader The reader being operated on.
* @param target The tag to read from, or @c NULL.
* @param bank The tag memory bank to read from.
* @param wordAddress The word address to start reading at.
* @param wordCount The number of words to read
* @param[out] data The read data.
*/
TMR_Status TMR_readTagMemWords(TMR_Reader *reader, TMR_TagFilter *target,
uint32_t bank, uint32_t wordAddress,
uint16_t wordCount, uint16_t data[]);
/**
* @deprecated This method is deprecated
*
* Write 8-bit bytes to the memory bank of a tag. If the tag's
* fundamental memory unit is larger than 8 bits, trying to write
* sub-unit quantities will produce an error.
*
* @param reader The reader to operate on.
* @param target The tag to write to, or @c NULL.
* @param bank The tag memory bank to write to.
* @param byteAddress The byte address to start writing to.
* @param byteCount The number of bytes to write.
* @param data The bytes to write.
*/
TMR_Status TMR_writeTagMemBytes(TMR_Reader *reader, TMR_TagFilter *target,
uint32_t bank, uint32_t byteAddress,
uint16_t byteCount, const uint8_t data[]);
/**
* @deprecated This method is deprecated
*
* Write 16-bit words to the memory bank of a tag. If the tag's
* fundamental memory unit is larger than 16 bits, trying to write
* sub-unit quantities will produce an error.
*
* @param reader The reader to operate on.
* @param target The tag to write to, or @c NULL.
* @param bank The tag memory bank to write to.
* @param wordAddress The word address to start writing to.
* @param wordCount The number of words to write.
* @param data The words to write.
*/
TMR_Status TMR_writeTagMemWords(TMR_Reader *reader, TMR_TagFilter *target,
uint32_t bank, uint32_t wordAddress,
uint16_t wordCount, const uint16_t data[]);
/**
* @ingroup reader
* Set the state of some GPO pins.
*
* @param reader The reader to operate on.
* @param count The length of the state array.
* @param state Array of reader pins and the state to set them to.
*/
TMR_Status TMR_gpoSet(TMR_Reader *reader, uint8_t count, const TMR_GpioPin state[]);
/**
* @ingroup reader
* Get the state of all GPI pins.
*
* @param reader The reader to operate on.
* @param[in] count Pointer to the allocated length of the state array.
* @param[out] count Pointer to the number of entries in the state array.
* @param[out] state Array of reader pins and the state to set them to.
*/
TMR_Status TMR_gpiGet(TMR_Reader *reader, uint8_t *count, TMR_GpioPin state[]);
/**
* @ingroup reader
* The TMR_firmwareLoad() method attempts to install firmware on the
* reader, then restart and reinitialize.
*
* @param reader The reader to operate on
* @param cookie Value to pass to the callback function.
* @param provider Callback function to provide firmware data.
*/
TMR_Status TMR_firmwareLoad(TMR_Reader *reader, void *cookie, TMR_FirmwareDataProvider provider);
/**
* Cookie for state storage of a TMR_memoryProvider.
*/
typedef struct TMR_memoryCookie {
/** Pointer to the start of the firmware image in memory */
uint8_t *firmwareStart;
/** Size of the firmware image */
uint32_t firmwareSize;
} TMR_memoryCookie;
/**
* This function can be used as a callback to TMR_firmwareLoad when
* the firmware image exists in system memory. The cookie is a pointer
* to a TMR_memoryCookie that is initialized with the start of the firmware
* image in memory and its size.
*
* @param cookie TMR_memoryCookie value.
* @param[in] size The number of bytes requested.
* @param[out] size The number of bytes returned.
* @param data Pointer to buffer to fill.
* @return true if there is more firmware data to return.
*/
bool TMR_memoryProvider(void *cookie, uint16_t *size, uint8_t *data);
/**
* This function can be used as a callback to TMR_firmwareLoad when
* the firmware image exists as a file.
*
* @param cookie FILE * pointing to the file to read from.
* @param[in] size The number of bytes requested.
* @param[out] size The number of bytes returned.
* @param data Pointer to buffer to fill.
* @return true if there is more firmware data to return.
*/
bool TMR_fileProvider(void *cookie, uint16_t *size, uint8_t *data);
/**
* @ingroup reader
* Set the value of a reader parameter.
*
* @param reader The reader to operate on.
* @param key The string identifying the parameter.
* @param value The new value to use for the parameter. The caller may
* not alter the value after passing it to this function.
*
* @test Call should fail if key is an invalid parameter name.
* @test Call should fail if key is valid but unsupported by connected reader.
* @test Call should succeed if key matches parameter name, independent of case.
*/
TMR_Status TMR_paramSet(struct TMR_Reader *reader, TMR_Param key, const void *value);
/**
* @ingroup reader
* Get the value of a reader parameter.
*
* @param reader The reader to operate on.
* @param key The string identifying the parameter.
* @param[out] value Pointer to the parameter value. For list types
* (including TMR_String), the caller must allocate the pointed-to
* space and set the size of the allocated space in the max field, and
* the function will write into that space and set the actual length
* of the data. If the list or string is larger than will fit in the
* pointed-to space, the length will be larger than the allocated
* space - be careful iterating over the results if there is a chance
* of not passing in a large enough structure.
*
* @test Call should fail if key is an invalid parameter name.
* @test Call should fail if key is valid but unsupported by connected reader.
* @test Call should succeed if key matches parameter name, independent of case.
*/
TMR_Status TMR_paramGet(struct TMR_Reader *reader, TMR_Param key, void *value);
/**
* @ingroup reader
* Reboot the reader
*
* @param reader The reader to operate on.
**/
TMR_Status TMR_reboot(struct TMR_Reader *reader);
/**
* Get a list of the parameters available
*
* Supported Parameters:
* @li /reader/antenna/checkPort
* @li /reader/antenna/connectedPortList
* @li /reader/antenna/portList
* @li /reader/antenna/portSwitchGpos
* @li /reader/antenna/returnLoss
* @li /reader/antenna/settlingTimeList
* @li /reader/antenna/txRxMap
* @li /reader/asyncofftime
* @li /reader/baudRate
* @li /reader/commandTimeout
* @li /reader/currentTime
* @li /reader/description
* @li /reader/extendedEpc
* @li /reader/gen2/BLF
* @li /reader/gen2/accessPassword
* @li /reader/gen2/bap
* @li /reader/gen2/protocolExtension
* @li /reader/gen2/q
* @li /reader/gen2/session
* @li /reader/gen2/tagEncoding
* @li /reader/gen2/target
* @li /reader/gen2/tari
* @li /reader/gen2/writeEarlyExit
* @li /reader/gen2/writeMode
* @li /reader/gen2/writeReplyTimeout
* @li /reader/gpio/inputList
* @li /reader/gpio/outputList
* @li /reader/hostname
* @li /reader/iso180006b/BLF
* @li /reader/iso180006b/delimiter
* @li /reader/iso180006b/modulationDepth
* @li /reader/licenseKey
* @li /reader/licensedFeatures
* @li /reader/metadataflags
* @li /reader/powerMode
* @li /reader/probeBaudRates
* @li /reader/radio/enablePowerSave
* @li /reader/radio/enableSJC
* @li /reader/radio/portReadPowerList
* @li /reader/radio/portWritePowerList
* @li /reader/radio/powerMax
* @li /reader/radio/powerMin
* @li /reader/radio/readPower
* @li /reader/radio/temperature
* @li /reader/radio/writePower
* @li /reader/read/asyncOffTime
* @li /reader/read/asyncOnTime
* @li /reader/read/plan
* @li /reader/region/hopTable
* @li /reader/region/hopTime
* @li /reader/region/id
* @li /reader/region/lbt/enable
* @li /reader/region/supportedRegions
* @li /reader/selectedProtocols
* @li /reader/statistics
* @li /reader/stats
* @li /reader/stats/enable
* @li /reader/status/antennaEnable
* @li /reader/status/frequencyEnable
* @li /reader/status/temperatureEnable
* @li /reader/tagReadData/enableReadFilter
* @li /reader/tagReadData/readFilterTimeout
* @li /reader/tagReadData/recordHighestRssi
* @li /reader/tagReadData/reportRssiInDbm
* @li /reader/tagReadData/tagopFailures
* @li /reader/tagReadData/tagopSuccesses
* @li /reader/tagReadData/uniqueByAntenna
* @li /reader/tagReadData/uniqueByData
* @li /reader/tagReadData/uniqueByProtocol
* @li /reader/tagop/antenna
* @li /reader/tagop/protocol
* @li /reader/transportTimeout
* @li /reader/trigger/read/Gpi
* @li /reader/uri
* @li /reader/userConfig
* @li /reader/userMode
* @li /reader/version/hardware
* @li /reader/version/model
* @li /reader/version/productGroup
* @li /reader/version/productGroupID
* @li /reader/version/productID
* @li /reader/version/serial
* @li /reader/version/software
* @li /reader/version/supportedProtocols
*
* @ingroup reader
*
* @param reader The reader to operate on.
* @param[out] keys Pointer to the list of parameters. The caller must
* allocate space for the parameters.
* @param[in] len Pointer to the allocated length of the space pointed to by keys.
* @param[out] len Pointer to the number of parameters supported by
* the reader, which may be larger or smaller than the provided
* array. If it is larger than the provided array, the list is
* truncated.
*/
TMR_Status TMR_paramList(struct TMR_Reader *reader, TMR_Param *keys, uint32_t *len);
/**
* @reader pointer to TMR_Reader
* @key pointer to TMR_Param
*/
void TMR_paramProbe (struct TMR_Reader *reader, TMR_Param key);
/**
* @ingroup reader
* Return the string name corresponding to a TMR_Param value.
* Only present if TMR_ENABLE_PARAM_STRINGS is set.
*
* @param key The parameter ID.
* @return The corresponding string name.
*/
const char* TMR_paramName(TMR_Param key);
/**
* @ingroup reader
* Return the TMR_Param ID corresponding to a string name.
* Only present if TMR_ENABLE_PARAM_STRINGS is set.
*
* @param name the parameter
* @return The TMR_Param value of the name, or TMR_PARAM_NONE if no such
* parameter exists.
*/
TMR_Param TMR_paramID(const char *name);
/**
* @ingroup reader
*
* Add a listener to the list of functions that will be called for
* each message sent to or received from the reader.
*
* @param reader The reader to operate on.
* @param block A structure containing a pointer to the listener
* function and a user-supplied cookie value to pass to the function
* when called.
*/
TMR_Status TMR_addTransportListener(TMR_Reader *reader, TMR_TransportListenerBlock *block);
/**
* @ingroup reader
*
* Remove a listener from the list of functions that will be called
* for each message sent to or received from the reader.
*
* @param reader The reader to operate on.
* @param block A structure containing a pointer to the listener
* function and a user-supplied cookie value to pass to the function
* when called.
*/
TMR_Status TMR_removeTransportListener(TMR_Reader *reader, TMR_TransportListenerBlock *block);
/**
* @ingroup reader
* Add a listener to the list of functions that will be called for
* each background tag read.
*
* @param reader The reader to operate on.
* @param block A structure containing a pointer to the listener
* function and a user-supplied cookie value to pass to the function
* when called.
*/
TMR_Status TMR_addReadListener(struct TMR_Reader *reader,
TMR_ReadListenerBlock *block);
/**
* @ingroup reader
* Add a listener to the list of functions that will be called for
* each background tag read.
*
* @param reader The reader to operate on.
* @param block A structure containing a pointer to the listener
* function and a user-supplied cookie value to pass to the function
* when called.
*/
TMR_Status TMR_addAuthReqListener(struct TMR_Reader *reader,
TMR_AuthReqListenerBlock *block);
/**
* @ingroup reader
* Remove a listener from the list of functions that will be called
* for each background tag read.
*
* @param reader The reader to operate on.
* @param block A structure containing a pointer to the listener
* function and a user-supplied cookie value to pass to the function
* when called.
*/
TMR_Status TMR_removeReadListener(struct TMR_Reader *reader,
TMR_ReadListenerBlock *block);
/**
* @ingroup reader
* Add a listener to the list of functions that will be called for
* each error that occurs during background tag reading.
*
* @param reader The reader to operate on.
* @param block A structure containing a pointer to the listener
* function and a user-supplied cookie value to pass to the function
* when called.
*/
TMR_Status TMR_addReadExceptionListener(struct TMR_Reader *reader,
TMR_ReadExceptionListenerBlock *block);
/**
* @ingroup reader
* Remove a listener from the list of functions that will be called
* for each error that occurs during background tag reading.
*
* @param reader The reader to operate on.
* @param block A structure containing a pointer to the listener
* function and a user-supplied cookie value to pass to the function
* when called.
*/
TMR_Status TMR_removeReadExceptionListener(struct TMR_Reader *reader,
TMR_ReadExceptionListenerBlock *block);
/**
* @ingroup reader
* Add a listener to the list of functions that will be called for
* each background status response.
*
* @param reader The reader to operate on.
* @param block A structure containing a pointer to the listener
* function and a user-supplied cookie value to pass to the function
* when called.
*/
TMR_Status TMR_addStatusListener(struct TMR_Reader *reader,
TMR_StatusListenerBlock *block);
/**
* @ingroup reader
* Remove a listener from the list of functions that will be called
* for each background status response.
*
* @param reader The reader to operate on.
* @param block A structure containing a pointer to the listener
* function and a user-supplied cookie value to pass to the function
* when called.
*/
TMR_Status TMR_removeStatusListener(struct TMR_Reader *reader,
TMR_StatusListenerBlock *block);
/**
* @ingroup reader
* Add a listener to the list of functions that will be called for
* each background status response.
*
* @param reader The reader to operate on.
* @param block A structure containing a pointer to the listener
* function and a user-supplied cookie value to pass to the function
* when called.
*/
TMR_Status TMR_addStatsListener(struct TMR_Reader *reader,
TMR_StatsListenerBlock *block);
/**
* @ingroup reader
* Remove a listener from the list of functions that will be called
* for each background status response.
*
* @param reader The reader to operate on.
* @param block A structure containing a pointer to the listener
* function and a user-supplied cookie value to pass to the function
* when called.
*/
TMR_Status TMR_removeStatsListener(struct TMR_Reader *reader,
TMR_StatsListenerBlock *block);
/**
* @ingroup reader
* Start reading tags in the background. The tags found will be passed
* to the registered read listeners, and any errors that occur during
* reading will be passed to the registered exception
* listeners. Reading will continue until stopReading() is called.
* The read listeners will be called from a background thread.
*
* @param reader The reader to operate on.
*/
TMR_Status TMR_startReading(struct TMR_Reader *reader);
TMR_Status TMR_receiveAutonomousReading(struct TMR_Reader *reader, TMR_TagReadData *trd, TMR_Reader_StatsValues *stats);
/**
* @ingroup reader
* Stop reading tags in the background. This function will wait until
* the reader has stopped.
*
* @param reader The reader to operate on.
*/
TMR_Status TMR_stopReading(struct TMR_Reader *reader);
/**
* @ingroup reader
* Stores the transport init function against the provided scheme.
*
* @param scheme the transport scheme name.
* @param nativeInit reference to the init function.
*/
TMR_Status TMR_setSerialTransport(char* scheme, TMR_TransportNativeInit nativeInit);
/**
* @ingroup reader
* This function will convert the error codes into proper error messages.
*
* @param reader The reader which resulted in error
* @param status The status code which is to be converted
*/
const char *TMR_strerr(TMR_Reader *reader, TMR_Status status);
/**
* @ingroup reader
* This function will initialize the
* TMR_StatValues structure with the default values
*/
TMR_Status TMR_STATS_init(TMR_Reader_StatsValues *stats);
/**
* @ingroup reader
* This function loads the reader configuration parameters from file and applies to module.
*
* @param reader The reader to operate on.
* @param filePath load reader configurations from filepath.
*/
TMR_Status TMR_loadConfig(struct TMR_Reader *reader, char *filePath);
/**
* @ingroup reader
* This function saves the current reader configuration parameters and its values to a file.
*
* @param reader The reader to operate on.
* @param filePath save reader configurations from filepath.
*/
TMR_Status TMR_saveConfig(struct TMR_Reader *reader, char *filePath);
#ifndef DOXYGEN_IGNORE
TMR_Status TMR_reader_init_internal(struct TMR_Reader *reader);
/*TMR_Status TMR_init_statusListenerBlock(TMR_StatusListenerBlock *slb, TMR_StatusListener listener,
void *cookie, TMR_SR_StatusContentFlags statusFlags);*/
TMR_Status validateReadPlan(TMR_Reader *reader, TMR_ReadPlan *plan, TMR_AntennaMapList *txRxMap, uint32_t protocols);
void TMR__notifyTransportListeners(TMR_Reader *reader, bool tx,
uint32_t dataLen, uint8_t *data,
int timeout);
void notify_exception_listeners(TMR_Reader *reader, TMR_Status status);
void cleanup_background_threads(TMR_Reader *reader);
#ifdef TMR_ENABLE_SERIAL_READER_ONLY
#define TMR_connect(reader) (TMR_SR_connect(reader))
#define TMR_destroy(reader) (TMR_SR_destroy(reader))
#define TMR_read(reader, timeoutMs, tagCount) (TMR_SR_read((reader),(timeoutMs),(tagCount)))
#define TMR_hasMoreTags(reader) (TMR_SR_hasMoreTags(reader))
#define TMR_getNextTag(reader, read) (TMR_SR_getNextTag((reader),(read)))
#define TMR_writeTag(reader, filter, data) (TMR_SR_writeTag((reader),(filter),(data)))
#define TMR_readTagMemWords(reader, target, bank, address, count, data) (TMR_SR_readTagMemWords((reader),(target),(bank),(address),(count),(data)))
#define TMR_readTagMemBytes(reader, target, bank, address, count, data) (TMR_SR_readTagMemBytes((reader),(target),(bank),(address),(count),(data)))
#define TMR_writeTagMemWords(reader, target, bank, address, count, data) (TMR_SR_writeTagMemWords((reader),(target),(bank),(address),(count),(data)))
#define TMR_writeTagMemBytes(reader, target, bank, address, count, data) (TMR_SR_writeTagMemBytes((reader),(target),(bank),(address),(count),(data)))
#define TMR_killTag(reader, filter, auth) (TMR_SR_killTag((reader),(filter),(auth)))
#define TMR_lockTag(reader, filter, action) (TMR_SR_lockTag((reader),(filter),(action)))
#define TMR_executeTagOp(reader, tagop, filter, data) (TMR_SR_executeTagOp((reader), (tagop), (filter), (data)))
#define TMR_gpoSet(reader, count, state) (TMR_SR_gpoSet((reader),(count),(state)))
#define TMR_gpiGet(reader, count, state) (TMR_SR_gpiGet((reader),(count),(state)))
#define TMR_firmwareLoad(reader, cookie, provider) (TMR_SR_firmwareLoad((reader),(cookie),(provider)))
#define TMR_reboot(reader) (TMR_SR_reboot((reader)))
#else
/**
* The fact that these functions are implemented via macros is an
* implementation detail, not something for the public API
* documentation.
*/
#define TMR_connect(reader) ((reader)->connect(reader))
#define TMR_destroy(reader) ((reader)->destroy(reader))
#define TMR_read(reader, timeoutMs, tagCount) ((reader)->read((reader),(timeoutMs),(tagCount)))
#define TMR_hasMoreTags(reader) ((reader)->hasMoreTags(reader))
#define TMR_getNextTag(reader, read) ((reader)->getNextTag((reader),(read)))
#define TMR_writeTag(reader, filter, data) ((reader)->writeTag((reader),(filter),(data)))
#define TMR_readTagMemWords(reader, target, bank, address, count, data) ((reader)->readTagMemWords((reader),(target),(bank),(address),(count),(data)))
#define TMR_readTagMemBytes(reader, target, bank, address, count, data) ((reader)->readTagMemBytes((reader),(target),(bank),(address),(count),(data)))
#define TMR_writeTagMemWords(reader, target, bank, address, count, data) ((reader)->writeTagMemWords((reader),(target),(bank),(address),(count),(data)))
#define TMR_writeTagMemBytes(reader, target, bank, address, count, data) ((reader)->writeTagMemBytes((reader),(target),(bank),(address),(count),(data)))
#define TMR_killTag(reader, filter, auth) ((reader)->killTag((reader),(filter),(auth)))
#define TMR_lockTag(reader, filter, action) ((reader)->lockTag((reader),(filter),(action)))
#define TMR_executeTagOp(reader, tagop, filter, data) ((reader)->executeTagOp((reader), (tagop), (filter), (data)))
#define TMR_gpoSet(reader, count, state) ((reader)->gpoSet((reader),(count),(state)))
#define TMR_gpiGet(reader, count, state) ((reader)->gpiGet((reader),(count),(state)))
#define TMR_firmwareLoad(reader, cookie, provider) ((reader)->firmwareLoad((reader),(cookie),(provider)))
#define TMR_modifyFlash(reader, sector, address, password, length, data, offset) ((reader->modifyFlash((reader),(sector),(address),(password),(length),(data),(offset)))
#define TMR_reboot(reader) ((reader)->reboot(reader))
#endif /* TMR_ENABLE_SERIAL_READER_ONLY */
#endif /* DOXYGEN_IGNORE */
#ifdef __cplusplus
}
#endif
#endif /* _TM_READER_H_ */