void KineticLogger_LogStatus(KineticProto_Status* status) { if (LogLevel < 0) { return; } ProtobufCMessage* protoMessage = (ProtobufCMessage*)status; KineticProto_Status_StatusCode code = status->code; if (code == KINETIC_PROTO_STATUS_STATUS_CODE_SUCCESS) { printf("Operation completed successfully\n"); } else if (code == KINETIC_PROTO_STATUS_STATUS_CODE_INVALID_STATUS_CODE) { printf("Operation was aborted!\n"); } else { // Output status code short name const ProtobufCMessageDescriptor* protoMessageDescriptor = protoMessage->descriptor; const ProtobufCFieldDescriptor* statusCodeDescriptor = protobuf_c_message_descriptor_get_field_by_name(protoMessageDescriptor, "code"); const ProtobufCEnumDescriptor* statusCodeEnumDescriptor = (ProtobufCEnumDescriptor*)statusCodeDescriptor->descriptor; const ProtobufCEnumValue* eStatusCodeVal = protobuf_c_enum_descriptor_get_value(statusCodeEnumDescriptor, code); KineticLogger_LogPrintf("Operation completed but failed w/error: %s=%d(%s)\n", statusCodeDescriptor->name, code, eStatusCodeVal->name); // Output status message, if supplied if (status->statusMessage) { const ProtobufCFieldDescriptor* statusMsgFieldDescriptor = protobuf_c_message_descriptor_get_field_by_name(protoMessageDescriptor, "statusMessage"); const ProtobufCMessageDescriptor* statusMsgDescriptor = (ProtobufCMessageDescriptor*)statusMsgFieldDescriptor->descriptor; KineticLogger_LogPrintf(" %s: '%s'", statusMsgDescriptor->name, status->statusMessage); } // Output detailed message, if supplied if (status->has_detailedMessage) { char tmp[8], msg[256]; const ProtobufCFieldDescriptor* statusDetailedMsgFieldDescriptor = protobuf_c_message_descriptor_get_field_by_name( protoMessageDescriptor, "detailedMessage"); const ProtobufCMessageDescriptor* statusDetailedMsgDescriptor = (ProtobufCMessageDescriptor*) statusDetailedMsgFieldDescriptor->descriptor; sprintf(msg, " %s: ", statusDetailedMsgDescriptor->name); for (size_t i = 0; i < status->detailedMessage.len; i++) { sprintf(tmp, "%02hhX", status->detailedMessage.data[i]); strcat(msg, tmp); } KineticLogger_LogPrintf(" %s", msg); } } }
int keyspec_export_ebuf(rw_keyspec_instance_t* instance, ProtobufCMessage* msg, const char* m_rname, const char* ts_fname, const char* es_fname) { RW_ASSERT(instance); /* * This is a kind of hack to export error records. * Assumptions about protobufc structure is made here. * Not worring as it is just a debug code. */ RW_ASSERT(msg); RW_ASSERT(m_rname); RW_ASSERT(ts_fname); RW_ASSERT(es_fname); const ProtobufCFieldDescriptor* mfdesc = protobuf_c_message_descriptor_get_field_by_name(msg->descriptor, m_rname); if (!mfdesc) { return 0; } // Make sure to assert all the assumptions! RW_ASSERT(mfdesc->type == PROTOBUF_C_TYPE_MESSAGE); RW_ASSERT(mfdesc->label == PROTOBUF_C_LABEL_REPEATED); RW_ASSERT(!(mfdesc->rw_flags & RW_PROTOBUF_FOPT_INLINE)); const ProtobufCFieldDescriptor* tsfdesc = protobuf_c_message_descriptor_get_field_by_name(mfdesc->msg_desc, ts_fname); if (!tsfdesc) { return 0; } RW_ASSERT(tsfdesc->type == PROTOBUF_C_TYPE_STRING); RW_ASSERT(tsfdesc->label == PROTOBUF_C_LABEL_OPTIONAL); RW_ASSERT(tsfdesc->rw_flags & RW_PROTOBUF_FOPT_INLINE); const ProtobufCFieldDescriptor* esfdesc = protobuf_c_message_descriptor_get_field_by_name(mfdesc->msg_desc, es_fname); if (!esfdesc) { return 0; } RW_ASSERT(esfdesc->type == PROTOBUF_C_TYPE_STRING); RW_ASSERT(esfdesc->label == PROTOBUF_C_LABEL_OPTIONAL); RW_ASSERT(esfdesc->rw_flags & RW_PROTOBUF_FOPT_INLINE); // Make sure that the field is not allocated earlier. RW_ASSERT(!STRUCT_MEMBER(ProtobufCMessage**, msg, mfdesc->offset)); RW_ASSERT(!STRUCT_MEMBER(uint32_t, msg, mfdesc->quantifier_offset)); CircularErrorBuffer& errorbuf = CircularErrorBuffer::get_instance(); ProtobufCMessage** records = (ProtobufCMessage **)protobuf_c_instance_alloc( instance->pbc_instance, errorbuf.get_capacity()*sizeof(void*)); // Caution! dont call any function that may log error. time_t stime = time(NULL); unsigned tot_records = 0; /* * Export the records in last-in-first out order so that the * recent errors are at the top. */ size_t idx = errorbuf.get_last_index(); size_t cap = errorbuf.get_capacity(); for (size_t c = 0; c < cap; c++) { const ErrRecord* r = errorbuf[idx]; if (!idx) { idx = (cap - 1); } else { idx--; } if (r->time <= stime && r->time ) { struct tm tm; localtime_r((const time_t*)(&r->time), &tm); ProtobufCMessage* record = (ProtobufCMessage *)protobuf_c_instance_alloc( instance->pbc_instance, mfdesc->msg_desc->sizeof_message); protobuf_c_message_init(mfdesc->msg_desc, record); char *tbuf = STRUCT_MEMBER_PTR(char, record, tsfdesc->offset); strftime(tbuf, tsfdesc->data_size, "%Y%m%d-%H%M%S", &tm); // Set the has field. STRUCT_MEMBER(uint32_t, record, tsfdesc->quantifier_offset) = 1; char *estr = STRUCT_MEMBER_PTR(char, record, esfdesc->offset); RW_ASSERT(esfdesc->data_size >= sizeof(r->errmsg)); strncpy(estr, (const char*)r->errmsg, sizeof(r->errmsg)-1); estr[sizeof(r->errmsg)-1] = 0; // Set the has field. STRUCT_MEMBER(uint32_t, record, esfdesc->quantifier_offset) = 1; records[tot_records++] = record; } } if (tot_records) { STRUCT_MEMBER(ProtobufCMessage**, msg, mfdesc->offset) = records; STRUCT_MEMBER(uint32_t, msg, mfdesc->quantifier_offset) = tot_records; } else {