34 #if defined(__linux__) || defined(__APPLE__)
54 #include <cutils/properties.h>
56 #define LOG_TAG "ni_rsrc_mon_logan"
63 static BOOL WINAPI console_ctrl_handler(DWORD ctrl_type)
89 #elif defined(__linux__)
90 void setup_signal_handler(
void);
100 void sig_handler(
int sig)
102 if (sig == SIGTERM || sig == SIGINT)
106 else if (sig == SIGHUP)
108 printf(
"SIGHUP, reloading p_config ? ");
109 setup_signal_handler();
120 void setup_signal_handler(
void)
122 if (signal(SIGTERM, sig_handler) == SIG_ERR ||
123 signal(SIGHUP, sig_handler) == SIG_ERR ||
124 signal(SIGINT, sig_handler) == SIG_ERR)
126 fprintf(stderr,
"Error %d: signal handler setup\n",
NI_ERRNO);
137 int get_numa_node(
const char *device_name)
143 char cmd_ret[64] = {0};
149 ptr = (
char *)(device_name + 5);
150 snprintf(cmd,
sizeof(cmd) - 1,
"cat /sys/block/%s/device/*/numa_node",ptr);
151 cmd_fp = popen(cmd,
"r");
156 if (fgets(cmd_ret,
sizeof(cmd_ret)/
sizeof(cmd_ret[0]), cmd_fp) == NULL)
186 const size_t len = strlen(numArray);
188 for (i = 0; i < len; i++)
190 if (!isdigit(numArray[i]))
192 fprintf(stderr,
"invalid, ABORTING\n");
197 return len == i ?
atoi(numArray) : 0;
210 if ( *(int32_t*)a < *(int32_t*)b )
return -1;
211 if ( *(int32_t*)a == *(int32_t*)b )
return 0;
212 if ( *(int32_t*)a > *(int32_t*)b )
return 1;
219 int32_t **module_ids,
220 int32_t *best_load_module_id)
222 unsigned int module_count;
227 snprintf(module_name,
sizeof(module_name),
"decoder");
228 *module_ids = (int32_t *)malloc(
sizeof(int32_t) * module_count);
231 fprintf(stderr,
"ERROR %d: Failed to allocate memory for ni_rsrc_mon print_perf()",
235 memcpy(*module_ids, coders->
decoders,
sizeof(int32_t) * module_count);
240 snprintf(module_name,
sizeof(module_name),
"encoder");
241 *module_ids = (int32_t *)malloc(
sizeof(int32_t) * module_count);
244 fprintf(stderr,
"ERROR %d: Failed to allocate memory for ni_rsrc_mon print_perf()",
248 memcpy(*module_ids, coders->
encoders,
sizeof(int32_t) * module_count);
252 fprintf(stderr,
"ERROR: wrong module type %d", module_type);
256 if (best_load_module_id)
258 memcpy((
void*)best_load_module_id, *module_ids,
sizeof(int32_t));
262 qsort(*module_ids, module_count,
sizeof(int32_t),
compareInt32_t);
282 int module_count = 0;
283 char module_name[8]={0};
284 int *module_id_arr = NULL;
285 int best_load_module_id = -1;
288 module_count =
get_modules(module_type, coders, module_name, &module_id_arr, &best_load_module_id);
290 if (outformattype == 0)
292 printf(
"Num %ss: %d\n", module_name, module_count);
296 if (outformattype == 0)
298 printf(
"%-4s %-5s %-4s %-10s %-4s %-4s %-14s %-20s\n",
"BEST",
"INDEX",
299 "LOAD",
"MODEL_LOAD",
"MEM",
"INST",
"DEVICE",
"NAMESPACE");
301 else if (outformattype == 2 || outformattype == 3)
305 printf(
"{\n \"decoders\": [\n");
309 printf(
" \"encoders\": [\n");
313 for (i = 0; i < module_count; i++)
318 if (p_device_context)
327 fprintf(stderr,
"Error open device %s, blk device %s\n",
336 if (NI_INVALID_EVENT_HANDLE == sessionCtxt->
event_handle)
340 fprintf(stderr,
"ERROR %d: print_perf() create envet\n",
NI_ERRNO);
353 fprintf(stderr,
"Error query %s %s %s.%d\n", module_name,
371 char best_load_print[2] =
" ";
374 strncpy(best_load_print,
"L", 1);
378 if(outformattype == 0)
380 printf(
"%s%s%s %-5d %-4d %-10d %-4d %-4d %-14s %-20s\n", best_load_print,
" ",
" ",
389 else if (outformattype == 1)
395 " \"%s\" : \"%s\",\n"
401 " \"%s\" : \"%s\",\n"
402 " \"%s\" : \"%s\",\n"
409 module_name,
"NUMBER", module_count,
"BEST", best_load_print,
422 else if (outformattype == 3)
426 " \"%s\" : \"%s\",\n"
432 " \"%s\" : \"%s\",\n"
433 " \"%s\" : \"%s\",\n"
440 "NUMBER", module_count,
"BEST", best_load_print,
454 if (i < module_count - 1)
467 " \"%s\" : \"%s\",\n"
473 " \"%s\" : \"%s\",\n"
474 " \"%s\" : \"%s\",\n"
479 "NUMBER", module_count,
"BEST", best_load_print,
491 if (i < module_count - 1)
504 if (outformattype == 2 || outformattype == 3)
525 if (!p_device_context)
531 if (p_session_context->
device_handle == NI_INVALID_DEVICE_HANDLE)
534 "ERROR: ni_device_open() failed for %s, errno %d\n",
542 if (NI_INVALID_EVENT_HANDLE == p_session_context->
event_handle)
546 fprintf(stderr,
"ERROR %d: open_and_get_log() create envet\n",
553 p_session_context->
hw_id =
562 return return_code ? false :
true;
568 unsigned int module_count;
569 int32_t *module_id_arr = NULL;
570 char module_name[8] = {0};
574 module_count =
get_modules(module_type, coders, module_name, &module_id_arr, NULL);
576 printf(
"Error: module not found!\n");
580 bool gen_log_file =
true;
582 void* p_log_buffer = NULL;
587 if (!p_device_context)
589 printf(
"Error: get device context failed, devid %d\n", devid);
595 if (!
open_and_get_log(p_device_context, sessionCtxt, &p_log_buffer, gen_log_file)) {
596 printf(
"Error: failed to dump fw log of card:%d blk_name:%s\n",
599 printf(
"Success: dumped fw log of card:%d blk_name:%s\n",
608 for (i = 0; i < module_count; i++)
611 if (!
open_and_get_log(p_device_context, sessionCtxt, &p_log_buffer, gen_log_file)) {
612 printf(
"Error: failed to dump fw log of card:%d blk_name:%s\n",
616 printf(
"Success: dumped fw log of card:%d blk_name:%s\n",
636 int main(
int argc,
char *argv[])
640 int should_match_rev = 1;
641 int init_no_compat_check = 0;
642 int init_only_if_full_compat = 0;
655 time_t startTime = { 0 }, now = { 0 };
656 int timeout_seconds = 0;
657 struct tm *ltime = NULL;
658 char buf[64] = { 0 };
659 long long time_diff_hours, time_diff_minutes, time_diff_seconds;
664 bool fw_log_dump =
false;
668 SetConsoleCtrlHandler(console_ctrl_handler, TRUE);
669 #elif defined(__linux__)
670 setup_signal_handler();
674 while ((opt =
getopt(argc, argv,
"hvrcn:o:t:D:k:l:i")) != -1)
680 if (!strcmp(
optarg,
"json"))
684 else if (!strcmp(
optarg,
"text"))
688 else if (!strcmp(
optarg,
"json1"))
692 else if (!strcmp(
optarg,
"json2"))
698 fprintf(stderr,
"Error: unknown selection for outputFormat: %s\n",
optarg);
707 init_no_compat_check = 1;
710 init_only_if_full_compat = 1;
714 printf(
"Timeout will be set %d\n", timeout_seconds);
723 if (!strcmp(
optarg,
"none")) {
725 }
else if (!strcmp(
optarg,
"fatal")) {
727 }
else if (!strcmp(
optarg,
"error")) {
729 }
else if (!strcmp(
optarg,
"info")) {
731 }
else if (!strcmp(
optarg,
"debug")) {
733 }
else if (!strcmp(
optarg,
"trace")) {
736 fprintf(stderr,
"unknown log level selected: %s",
optarg);
749 printf(
"-------- ni_rsrc_mon_logan v%s --------\n"
750 "The ni_rsrc_mon_logan program provides a real-time view of NETINT Logan T4XX \n"
751 "resources running on the system.\n"
752 "return 0 on success\n"
753 "return 1 on failure\n"
754 "Usage: sudo ni_rsrc_mon_logan [OPTIONS]\n"
755 "-o Output print format: text|json||json2\n"
756 "-n Specify reporting interval in one second interval.\n"
757 " If 0 or no selection, report only once.\n Default: 0\n"
758 "-r Init transcoder card resource regardless firmware release \n"
759 " version to libxcoder_logan version compatibility.\n"
760 " Default: only init cards with compatible firmware version.\n"
761 "-c Only init if all cards are fully compatible. Default is to init as many \n"
762 " fully and partially cards as possible."
763 "-t Set timeout time in seconds for device polling. Program will \n"
764 " exit with failure if timeout is reached without finding at \n"
765 " least one device. If 0 or no selection, poll indefinitely \n"
766 " until a T4XX device is found.\n"
768 "-D Dump firmware logs to current directory. Default: 0(not dump fw log).\n"
769 "-k Specify to dump which card's firmware logs.\n"
770 " Default: -1(dump fw log of all cards).\n"
771 "-l Set loglevel of libxcoder_logan API.\n"
772 " [none, fatal, error, info, debug, trace]\n"
774 "-v Show libxcoder_logan version.\n"
775 "-i Do not refresh the devices list.\n"
776 "-h Open this help message.\n"
778 "Reporting columns\n"
779 "BEST flag showing card of lowest realtime load and to be selected for \n"
780 " next auto allocated job\n"
781 "INDEX index number used by resource manager to identify the resource\n"
782 "LOAD realtime load\n"
783 "MODEL_LOAD estimated load based on framerate and resolution\n"
784 "INST number of job instances\n"
785 "DEVICE path to NVMe device file handle\n"
790 fprintf(stderr,
"Option -o, -n, or -l require an argument, use option -h for help, "
791 "all other options are not supported.\n");
793 #elif defined(__linux__)
796 fprintf(stderr,
"Option -%c requires an argument.\n",
optopt);
801 fprintf(stderr,
"Unknown option `-%c'.\n",
optopt);
806 fprintf(stderr,
"Unknown option character `\\x%x'.\n",
optopt);
812 fprintf(stderr,
"ABORTING\n");
817 if (init_no_compat_check && init_only_if_full_compat)
819 fprintf(stderr,
"Error: -r option cannot be used with -c option\n");
822 if (init_no_compat_check)
824 should_match_rev = 0;
826 else if (init_only_if_full_compat)
828 should_match_rev = 2;
831 if ((argc <= 2) && (
optind == 1))
845 fprintf(stderr,
"Error access NI resource, quit ..\n");
852 fprintf(stderr,
"Error get Coders info ..\n");
860 printf(
"**************************************************\n");
863 startTime = time(NULL);
867 ltime = localtime(&now);
870 strftime(buf,
sizeof(buf),
"%c", ltime);
872 time_diff_seconds = (
long long)difftime(now, startTime);
873 time_diff_minutes = time_diff_seconds / 60;
874 time_diff_hours = time_diff_minutes / 60;
880 printf(
"Error: resource pool records might be corrupted!!\n");
887 printf(
"%s up %02lld" ":%02lld" ":%02lld" " v%s\n", buf, time_diff_hours, time_diff_minutes % 60, time_diff_seconds % 60,
894 if (WAIT_ABANDONED == WaitForSingleObject(p_device_pool->
lock, INFINITE))
896 fprintf(stderr,
"ERROR: Failed to obtain mutex: %p\n", p_device_pool->
lock);
899 #elif defined(__linux__)
900 if ( flock(p_device_pool->
lock, LOCK_EX) )
902 fprintf(stderr,
"Error flock() failed\n");
909 ReleaseMutex((HANDLE)p_device_pool->
lock);
910 #elif defined(__linux__)
911 if ( flock(p_device_pool->
lock, LOCK_UN) )
913 fprintf(stderr,
"Error flock() failed\n");
922 printf(
"**************************************************\n");
927 if (checkInterval == 0)
939 if (WAIT_ABANDONED == WaitForSingleObject(p_device_pool->
lock, INFINITE))
941 fprintf(stderr,
"ERROR: Failed to obtain mutex: %p\n", p_device_pool->
lock);
944 if ( lockf(p_device_pool->
lock, F_LOCK, 0) )
946 perror(
"ERROR: cannot lock p_device_pool");
951 ReleaseMutex((HANDLE)p_device_pool->
lock);
953 if ( lockf(p_device_pool->
lock, F_ULOCK, 0) )
955 perror(
"ERROR: cannot unlock p_device_pool");
964 system(
"chmod -R 777 /dev/shm_netint/");
965 system(
"chmod 777 /dev/block/nvme* 2>/dev/null");
966 system(
"chmod 777 /dev/nvme* 2>/dev/null");
967 property_set(
"ni_rsrc_init_logan_completed",
"yes");
Common NETINT definitions used by all modules.
@ NI_LOGAN_RETCODE_SUCCESS
#define NI_LOGAN_XCODER_REVISION
@ NI_LOGAN_DEVICE_TYPE_ENCODER
@ NI_LOGAN_DEVICE_TYPE_DECODER
ni_device_handle_t ni_logan_device_open(const char *p_dev, uint32_t *p_max_io_size_out)
Opens device and returnes device device_handle if successful.
ni_logan_retcode_t ni_logan_device_session_query(ni_logan_session_context_t *p_ctx, ni_logan_device_type_t device_type)
Query session data from the device - Currently not implemented If device_type is NI_LOGAN_DEVICE_TYPE...
void ni_logan_device_session_context_init(ni_logan_session_context_t *p_ctx)
Initialize already allocated session context to a known state.
void ni_logan_close_event(ni_event_handle_t event_handle)
Closes event and releases resources.
void ni_logan_device_session_context_clear(ni_logan_session_context_t *p_ctx)
Clear already allocated session context to all zeros.
ni_logan_retcode_t ni_logan_alloc_and_get_fw_logs(ni_logan_session_context_t *p_ctx, void **p_log_buffer, bool gen_log_file)
Allocate log buffer if needed and retrieve firmware logs from device.
ni_event_handle_t ni_logan_create_event(void)
Create event and returnes event handle if successful.
void ni_logan_device_close(ni_device_handle_t device_handle)
Closes device and releases resources.
Main NETINT device API header file provides the ability to communicate with NI T-408 type hardware tr...
int getopt(int argc, char *argv[], const char *optstring)
void ni_log_set_level(ni_log_level_t level)
Set ni_log_level.
ni_logan_device_context_t * ni_logan_rsrc_get_device_context(ni_logan_device_type_t device_type, int guid)
Allocates and returns a pointer to ni_logan_device_context_t struct based on provided device_type and...
void ni_logan_rsrc_free_device_pool(ni_logan_device_pool_t *p_device_pool)
Free all resources taken by the device pool.
void ni_logan_rsrc_free_device_context(ni_logan_device_context_t *p_device_context)
Free previously allocated device context.
int ni_logan_rsrc_init(int should_match_rev, int timeout_seconds)
Initialize and create all resources required to work with NETINT NVMe transcoder devices....
ni_logan_retcode_t ni_logan_rsrc_refresh(int should_match_rev)
Scan and refresh all resources on the host, taking into account hot-plugged and pulled out cards.
ni_logan_device_pool_t * ni_logan_rsrc_get_device_pool(void)
Create and return the allocated ni_logan_device_pool_t struct.
Exported definitions related to resource management of NI T-408 devices.
int main(int argc, char *argv[])
int compareInt32_t(const void *a, const void *b)
compare two int32_t for qsort
void dump_fw_log(ni_logan_device_queue_t *coders, ni_logan_session_context_t *sessionCtxt, int devid)
int argToI(char *numArray)
convert number from argv input to integer if safe
void print_perf(ni_logan_device_type_t module_type, ni_logan_device_queue_t *coders, ni_logan_session_context_t *sessionCtxt, int outformattype)
print performance data for either decoder or encoder
unsigned int get_modules(ni_logan_device_type_t module_type, ni_logan_device_queue_t *coders, char *module_name, int32_t **module_ids, int32_t *best_load_module_id)
bool open_and_get_log(ni_logan_device_context_t *p_device_context, ni_logan_session_context_t *p_session_context, void **p_log_buffer, bool gen_log_file)
uint32_t g_logan_xcoder_stop_process
Private definitions related to resource management of NI T-408 devices.
void ni_logan_usleep(int64_t usec)
Exported utility routines definition.
ni_logan_device_info_t * p_device_info
char dev_name[NI_LOGAN_MAX_DEVICE_NAME_LEN]
char blk_name[NI_LOGAN_MAX_DEVICE_NAME_LEN]
ni_logan_device_queue_t * p_device_queue
int32_t decoders[LOGAN_MAX_DEVICE_CNT]
int32_t encoders[LOGAN_MAX_DEVICE_CNT]
uint32_t fw_video_mem_usage
ni_logan_load_query_t load_query
ni_device_handle_t device_handle
ni_event_handle_t event_handle
ni_device_handle_t blk_io_handle
uint32_t max_nvme_io_size
uint8_t composite_temperature