8 Replies Latest reply on Aug 20, 2018 4:43 AM by PhDi_1589426

    CYBLE_EVT_GATTS_READ_REQ - Identify which characteristic was read




      Is it possible to determine which characteristic was read when the CYBLE_EVT_GATTS_READ_REQ event is triggered?


      I would like to update the contents of a custom characteristic every time it is read to facilitate a memory dump process.  Currently it is a bit slow having to send a Write and then a Read for each block of data.  If each read caused the characteristic to be updated with the next block of data to allow the next read to get the next block, that would significantly improve performance for my application.


      Any thoughts as to how I could accomplish this?




      - Chris

        • 1. Re: CYBLE_EVT_GATTS_READ_REQ - Identify which characteristic was read

          Hi Chris,


          The CYBLE_EVT_GATTS_READ_CHAR_VAL_ACCESS_REQ stack event generates an event with the parameter of a pointer of type CYBLE_GATTS_CHAR_VAL_READ_REQ_T. This has the attrHandle member, which you should be able to use to identify the characteristic in question.

          1 of 1 people found this helpful
          • 2. Re: CYBLE_EVT_GATTS_READ_REQ - Identify which characteristic was read

            Thanks jrow.  I will look into that and update this thread if everything works.


            - Chris

            • 3. Re: CYBLE_EVT_GATTS_READ_REQ - Identify which characteristic was read

              This code appears to work well for this.




              CYBLE_GATTS_CHAR_VAL_READ_REQ_T *rdReqParam;






                 rdReqParam = (CYBLE_GATTS_CHAR_VAL_READ_REQ_T *) eventParam;


                 if (rdReqParam->attrHandle == CYBLE_SERVICE_CHARACTERISTIC_CHAR_HANDLE) {


                    // Act on it







              1 of 1 people found this helpful
              • 4. Re: CYBLE_EVT_GATTS_READ_REQ - Identify which characteristic was read

                I had the same problem and it works fine, thanks!



                I have another question about CYBLE_EVT_GATTS_READ_CHAR_VAL_ACCESS_REQ . I notice that this stack event is called 6 times. Do you know why? I read the characteristic from Android phone and then in a CYBLE_EVT_GATTS_READ_CHAR_VAL_ACCESS_REQ stack event I read an eeprom and I update the characteristic value:


                               /* Update READ EEPROM handle with new values */

                                readHandle.attrHandle = CYBLE_READ_EEPROM_SERVICE_READ_EEPROM_CHAR_HANDLE;

                                readHandle.value.len = 0x80 ;

                                readHandle.value.val = eeprom;           


                                /* Update the READ EEPROM attribute value*/

                                CyBle_GattsWriteAttributeValue(&readHandle, 0x00, &cyBle_connHandle, 0);


                Do you know what is happening?


                Many thanks,



                • 5. Re: CYBLE_EVT_GATTS_READ_REQ - Identify which characteristic was read

                  I have a similar request, but I keep getting an error that my param is uninitialized. I have not tested yet, but I am sure without the param being initialized it will not work.


                  I am just trying to update the value STATUS from the variable Status when it is called for by the CLIENT.

                  Here is the pertinent code:


                  #define STATUS_CHAR_DATA_LEN 1

                  uint8 Status = 0;


                  CYBLE_GATTS_CHAR_VAL_READ_REQ_T *read_request_param;



                                  if(CYBLE_STATUS_STATUS_CHAR_HANDLE == read_request_param->connHandle.attId)


                                      STATUS.attrHandle = CYBLE_STATUS_STATUS_CHAR_HANDLE;

                                      STATUS.value.val = &Status;

                                      STATUS.value.actualLen = STATUS_CHAR_DATA_LEN;



                  • 6. Re: CYBLE_EVT_GATTS_READ_REQ - Identify which characteristic was read

                    Hi Herb,


                    i think you should change

                    "if(CYBLE_STATUS_STATUS_CHAR_HANDLE == read_request_param->connHandle.attId)"


                    "if(CYBLE_STATUS_STATUS_CHAR_HANDLE == read_request_param->handleValPair.attrHandle)".


                    There is one more thing. If your read_request_param is a pointer you can use the "->" Operator.

                    If it is a variable you can use the "." Operator.




                    • 7. Re: CYBLE_EVT_GATTS_READ_REQ - Identify which characteristic was read

                      Philipp, I cannot get the tool to allow that variable.  There is no handleValPair, here is the definition from StackGATTServer.h.


                      Here is the error I get, as you can see the


                      BLE_Handler.c:102:79: warning: 'read_request_param' may be used uninitialized in this function [-Wmaybe-uninitialized]

                                       if(CYBLE_STATUS_STATUS_VALUE_CHAR_HANDLE == read_request_param->attrHandle)



                      /** Event parameters for characteristic read value access

                      * even generated by BLE Stack upon an access of Characteristic value

                      * read for the characteristic definition which has

                      * CYBLE_GATT_DB_ATTR_CHAR_VAL_RD_EVENT property set.


                      typedef struct


                          /** Connection handle */

                          CYBLE_CONN_HANDLE_T             connHandle;



                          /** Attribute Handle*/

                          CYBLE_GATT_DB_ATTR_HANDLE_T     attrHandle;



                          /** Output Param: Profile/Service specific error code,

                           * profile or application need to change this

                           * to service specific error based on service/profile

                           * requirements. */

                          CYBLE_GATT_ERR_CODE_T           gattErrorCode;




                      • 8. Re: CYBLE_EVT_GATTS_READ_REQ - Identify which characteristic was read

                        Hi Herb,


                        sorry for the delay. I have been on vacation. It seems like you use PSoC 4 BLE.

                        You need to initialize it with a typecast on eventParam.


                        I have an exsample for PSoC 4 that might be helpful.


                                case CYBLE_EVT_GATTS_WRITE_CMD_REQ:

                                case CYBLE_EVT_GATTS_WRITE_REQ:                                 // This event is generated when the connected Central device                                                                                                          sends a Write request. Event parameter is a pointer to a structure of                                                                                                          type CYBLE_GATTS_WRITE_REQ_PARAM_T

                                    printf ("GATT Server Write Request \r\n");                       // The parameter contains the data written


                                    ProcessWriteReq(eventParam);                                   // Function to process Write Requests

                                    DisplayArray();                                                            // Display the current RGB Array in the UART Terminal

                                   CyBle_GattsWriteRsp(cyBle_connHandle);                      // Send the response to the write request. Parameter is the actual                                                                                           connection handle




                        void ProcessWriteReq(void * eventParam)


                                        CYBLE_GATTS_WRITE_REQ_PARAM_T *wrReqParam;             


                                        wrReqParam = (CYBLE_GATTS_WRITE_REQ_PARAM_T *) eventParam;             // Extract the Write data sent by Client


                                       if(CYBLE_RGB_LED_SERVICE_RGB_LED_CHARACTERISTIC_CHAR_HANDLE ==                     wrReqParam->handleValPair.attrHandle)        



                                                      RGBledData[RED_INDEX] = wrReqParam->handleValPair.value.val[RED_INDEX];                // Store RGB LED data                                                                                                                                                                                     in local array

                                                       RGBledData[GREEN_INDEX] = wrReqParam->handleValPair.value.val[GREEN_INDEX];

                                                       RGBledData[BLUE_INDEX] = wrReqParam->handleValPair.value.val[BLUE_INDEX];

                                                       RGBledData[INTENSITY_INDEX] = wrReqParam->handleValPair.value.val[INTENSITY_INDEX];


                                                       UpdateRGBLED(RGBledData, sizeof(RGBledData));           // Update the PrISM component density value to                                                                                                                                   represent color */