Merge branch 'RU-RAU-split' of https://gitlab.eurecom.fr/oai/openairinterface5g into RU-RAU-split
This commit is contained in:
@@ -54,7 +54,7 @@ char defbool[2]="1";
|
||||
} else { /* boolean value */
|
||||
tmpval = defbool;
|
||||
}
|
||||
printf("cc 0x%08x, %i\n",tmpval,argok);
|
||||
|
||||
switch(cfgoptions->type)
|
||||
{
|
||||
case TYPE_STRING:
|
||||
|
||||
@@ -0,0 +1,52 @@
|
||||
cmake_minimum_required(VERSION 2.8 FATAL_ERROR)
|
||||
IF(DEFINED ENV{OPENAIR_DIR})
|
||||
message("...using oai source files in $ENV{OPENAIR_DIR}")
|
||||
ELSE()
|
||||
message("OPENAIR_DIR is not defined. You must run \"source oaienv\" from the oai root dir")
|
||||
# exit early
|
||||
return()
|
||||
ENDIF()
|
||||
|
||||
|
||||
set(APPROOT . )
|
||||
set(OPENAIR_DIR $ENV{OPENAIR_DIR})
|
||||
set(OPENAIR_BUILD_DIR $ENV{OPENAIR_DIR}/cmake_targets)
|
||||
set(OPENAIR1_DIR $ENV{OPENAIR1_DIR})
|
||||
set(OPENAIR2_DIR $ENV{OPENAIR2_DIR})
|
||||
set(OPENAIR_PHY_DIR $ENV{OPENAIR1_DIR}/PHY)
|
||||
set(OPENAIR_TARGET_DIR $ENV{OPENAIR_DIR}/targets)
|
||||
set(OPENAIR_COMMONUTILS_DIR $ENV{OPENAIR_DIR}/common/utils)
|
||||
set(OPENAIR2_COMMON_DIR $ENV{OPENAIR_DIR}/openair2/COMMON)
|
||||
set(OPENAIR_ASN1INC ${OPENAIR_BUILD_DIR}/lte_build_oai/build/CMakeFiles/Rel14)
|
||||
set(OPENAIR_NFAPIINC $ENV{NFAPI_DIR} )
|
||||
|
||||
set(CMAKE_INSTALL_PREFIX $ENV{OPENAIR_TARGETS})
|
||||
|
||||
add_definitions (-DRel14 -DCMAKER -DENABLE_FXP -DENABLE_ITTI -DENABLE_NAS_UE_LOGGING -DENABLE_SECURITY -DENABLE_USE_CPU_EXECUTION_TIME -DENABLE_USE_MME -DENABLE_VCD -DENB_AGENT -DENB_MODE -DETHERNET=1 -DEXMIMO_IOT -DJUMBO_FRAME -DLINK_ENB_PDCP_TO_GTPV1U -DLOG_NO_THREAD -DMAC_CONTEXT -DMAX_NUM_CCs=1 -DNAS_BUILT_IN_UE -DNAS_UE -DNB_ANTENNAS_RX=2 -DNB_ANTENNAS_TX=2 -DNB_ANTENNAS_TXRX=2 -DNEW_FFT -DNO_RRM -DNone=1 -DOAI_NW_DRIVER_USE_NETLINK -DOPENAIR1 -DOPENAIR2 -DOPENAIR_LTE -DPC_DSP -DPC_TARGET -DPHYSIM -DPHY_CONTEXT -DPUCCH -DRel10=1 -DS1AP_VERSION=R10 -DTRACE_RLC_MUTEX -DUSER_MODE -DX2AP_VERSION=R11 -DXFORMS -mavx2 -msse4.1 -mssse3)
|
||||
add_compile_options( -fPIC -march=native -Ofast)
|
||||
|
||||
include_directories( ./ ${OPENAIR_COMMON_DIR} ${OPENAIR_DIR} ${OPENAIR1_DIR} ${OPENAIR2_DIR} ${OPENAIR2_COMMON_DIR} ${OPENAIR2_DIR}/UTIL/LOG
|
||||
${OPENAIR_COMMONUTILS_DIR}/msc ${OPENAIR_COMMONUTILS_DIR}/itti ${OPENAIR_ASN1INC} ${OPENAIR_TARGET_DIR}/COMMON ${OPENAIR_TARGET_DIR}/ARCH/COMMON
|
||||
${OPENAIR_NFAPIINC})
|
||||
|
||||
set(TELNETSRV_SOURCE
|
||||
${APPROOT}/telnetsrv.c
|
||||
${APPROOT}/telnetsrv_phycmd.c
|
||||
${APPROOT}/telnetsrv_proccmd.c
|
||||
)
|
||||
|
||||
#set(TELNETSRV_ETHDEVCMD_SOURCE
|
||||
# ${APPROOT}/telnetsrv/telnetsrv_ethdevcmd.c
|
||||
# )
|
||||
|
||||
|
||||
|
||||
add_library(telnetsrv MODULE ${TELNETSRV_SOURCE} )
|
||||
#add_library(telnetsrv_ethdevcmd MODULE ${TELNETSRV_ETHDEVCMD_SOURCE} )
|
||||
|
||||
|
||||
install(TARGETS telnetsrv DESTINATION bin)
|
||||
|
||||
if (EXISTS "${OPENAIR_BUILD_DIR}/lte_build_oai/build" AND IS_DIRECTORY "${OPENAIR_BUILD_DIR}/lte_build_oai/build")
|
||||
install(TARGETS telnetsrv DESTINATION ${OPENAIR_BUILD_DIR}/lte_build_oai/build)
|
||||
endif (EXISTS "${OPENAIR_BUILD_DIR}/lte_build_oai/build" AND IS_DIRECTORY "${OPENAIR_BUILD_DIR}/lte_build_oai/build")
|
||||
@@ -0,0 +1,45 @@
|
||||
|
||||
/* FT NOKBLF:
|
||||
* this source is to be linked with the program using the telnet server, it looks for
|
||||
* the telnet server dynamic library, possibly loads it and calls the telnet server
|
||||
* init functions
|
||||
*/
|
||||
#define _GNU_SOURCE
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <unistd.h>
|
||||
#include <string.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <dlfcn.h>
|
||||
#include "telnetsrv.h"
|
||||
#include "openair1/PHY/defs.h"
|
||||
|
||||
int load_telnet(void)
|
||||
{
|
||||
void *lib_handle;
|
||||
initfunc_t fpi;
|
||||
|
||||
|
||||
lib_handle = dlopen(TELNETSRV_SHAREDLIB, RTLD_LAZY|RTLD_NODELETE|RTLD_GLOBAL);
|
||||
if (!lib_handle)
|
||||
{
|
||||
printf("[TELNETSRV] telnet server is not loaded: %s\n", dlerror());
|
||||
return -1;
|
||||
}
|
||||
|
||||
fpi = dlsym(lib_handle,"init_telnetsrv");
|
||||
|
||||
if (fpi != NULL )
|
||||
{
|
||||
fpi(cfgfile);
|
||||
}
|
||||
else
|
||||
{
|
||||
fprintf(stderr,"[TELNETSRV] %s %d Telnet server init function not found %s\n",__FILE__, __LINE__, dlerror());
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
dlclose(lib_handle);
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
#ifndef TELNET_LOAD_H
|
||||
#define TELNET_LOAD_H
|
||||
#include "telnetsrv.h"
|
||||
extern int load_telnet(void);
|
||||
#endif
|
||||
@@ -0,0 +1,696 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file common/utils/telnetsrv.c
|
||||
* \brief: implementation of a telnet server
|
||||
* \author Francois TABURET
|
||||
* \date 2017
|
||||
* \version 0.1
|
||||
* \company NOKIA BellLabs France
|
||||
* \email: francois.taburet@nokia-bell-labs.com
|
||||
* \note
|
||||
* \warning
|
||||
*/
|
||||
#define _GNU_SOURCE
|
||||
#include <sys/types.h>
|
||||
#include <sys/socket.h>
|
||||
#include <netinet/in.h>
|
||||
#include <arpa/inet.h>
|
||||
#include <netdb.h>
|
||||
#include <stdio.h>
|
||||
#include <unistd.h>
|
||||
#include <fcntl.h>
|
||||
#include <errno.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <signal.h>
|
||||
#include <pthread.h>
|
||||
#include <telnetsrv.h>
|
||||
#include <string.h>
|
||||
#include <stdarg.h>
|
||||
#include <unistd.h>
|
||||
#include <fcntl.h>
|
||||
#include <dlfcn.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/resource.h>
|
||||
|
||||
#include "common/config/config_userapi.h"
|
||||
|
||||
|
||||
#include "telnetsrv_phycmd.h"
|
||||
#include "telnetsrv_proccmd.h"
|
||||
static char* telnet_defstatmod[] = {"softmodem","phy"};
|
||||
static telnetsrv_params_t telnetparams;
|
||||
#define TELNETSRV_LISTENADDR 0
|
||||
#define TELNETSRV_LISTENPORT 1
|
||||
#define TELNETSRV_PRIORITY 2
|
||||
#define TELNETSRV_DEBUG 3
|
||||
#define TELNETSRV_STATICMOD 7
|
||||
#define TELNETSRV_SHRMOD 8
|
||||
paramdef_t telnetoptions[] = {
|
||||
/*--------------------------------------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
/* configuration parameters for telnet utility */
|
||||
/* optname helpstr paramflags XXXptr defXXXval type numelt */
|
||||
/*--------------------------------------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{"listenaddr", "<listen ip address>", 0, uptr:&telnetparams.listenaddr, defstrval:"0.0.0.0", TYPE_IPV4ADDR, 0 },
|
||||
{"listenport", "<local port>", 0, uptr:&(telnetparams.listenport), defuintval:9090, TYPE_UINT, 0 },
|
||||
{"priority", "<scheduling policy (0-99)", 0, uptr:&telnetparams.priority, defuintval:0, TYPE_INT, 0 },
|
||||
{"debug", "<debug level>", 0, uptr:NULL, defuintval:0, TYPE_UINT, 0 },
|
||||
{"loopcount", "<loop command iterations>", 0, uptr:&(telnetparams.loopcount), defuintval:10, TYPE_UINT, 0 },
|
||||
{"loopdelay", "<loop command delay (ms)>", 0, uptr:&(telnetparams.loopdelay), defuintval:5000, TYPE_UINT, 0 },
|
||||
{"phypbsize", "<phy dump buff size (bytes)>",0, uptr:&(telnetparams.phyprntbuff_size),defuintval:65000, TYPE_UINT, 0 },
|
||||
{"staticmod", "<static modules selection>", 0, NULL, defstrlistval:telnet_defstatmod,TYPE_STRINGLIST,1},
|
||||
{"shrmod", "<static modules selection>", 0, NULL, NULL,TYPE_STRINGLIST,0 },
|
||||
};
|
||||
|
||||
int get_phybsize() {return telnetparams.phyprntbuff_size; };
|
||||
int add_telnetcmd(char *modulename,telnetshell_vardef_t *var, telnetshell_cmddef_t *cmd );
|
||||
int setoutput(char *buff, int debug, telnet_printfunc_t prnt);
|
||||
int setparam(char *buff, int debug, telnet_printfunc_t prnt);
|
||||
|
||||
telnetshell_vardef_t telnet_vardef[] = {
|
||||
{"debug",TELNET_VARTYPE_INT32,&telnetparams.telnetdbg},
|
||||
{"prio",TELNET_VARTYPE_INT32,&telnetparams.priority},
|
||||
{"loopc",TELNET_VARTYPE_INT32,&telnetparams.loopcount},
|
||||
{"loopd",TELNET_VARTYPE_INT32,&telnetparams.loopdelay},
|
||||
{"phypb",TELNET_VARTYPE_INT32,&telnetparams.phyprntbuff_size},
|
||||
{"",0,NULL}
|
||||
};
|
||||
|
||||
telnetshell_cmddef_t telnet_cmdarray[] = {
|
||||
{"redirlog","[here,file,off]",setoutput},
|
||||
{"param","[prio]",setparam},
|
||||
{"","",NULL},
|
||||
};
|
||||
|
||||
|
||||
void client_printf(const char *message, ...)
|
||||
{
|
||||
va_list va_args;
|
||||
|
||||
va_start(va_args, message);
|
||||
if (telnetparams.new_socket > 0)
|
||||
{
|
||||
vsnprintf(telnetparams.msgbuff,sizeof(telnetparams.msgbuff)-1,message, va_args);
|
||||
send(telnetparams.new_socket,telnetparams.msgbuff , strlen(telnetparams.msgbuff), MSG_NOSIGNAL);
|
||||
}
|
||||
else
|
||||
{
|
||||
vprintf(message, va_args);
|
||||
}
|
||||
va_end(va_args);
|
||||
return ;
|
||||
}
|
||||
|
||||
#define NICE_MAX 19
|
||||
#define NICE_MIN -20
|
||||
void set_sched(pthread_t tid, int pid, int priority)
|
||||
{
|
||||
int rt;
|
||||
struct sched_param schedp;
|
||||
int policy;
|
||||
char strpolicy[10];
|
||||
|
||||
|
||||
//sched_get_priority_max(SCHED_FIFO)
|
||||
if (priority < NICE_MIN)
|
||||
{
|
||||
policy=SCHED_FIFO;
|
||||
sprintf(strpolicy,"%s","fifo");
|
||||
schedp.sched_priority= NICE_MIN - priority ;
|
||||
}
|
||||
else if (priority > NICE_MAX)
|
||||
{
|
||||
policy=SCHED_IDLE;
|
||||
sprintf(strpolicy,"%s","idle");
|
||||
schedp.sched_priority=0;
|
||||
}
|
||||
else
|
||||
{
|
||||
policy=SCHED_OTHER;
|
||||
sprintf(strpolicy,"%s","other");
|
||||
schedp.sched_priority=0;
|
||||
}
|
||||
if( tid != 0)
|
||||
{
|
||||
rt = pthread_setschedparam(tid, policy, &schedp);
|
||||
}
|
||||
else if(pid > 0)
|
||||
{
|
||||
rt = sched_setscheduler( pid, policy,&schedp);
|
||||
}
|
||||
if (rt != 0)
|
||||
{
|
||||
client_printf("Error %i: %s modifying sched param to %s:%i, \n",
|
||||
errno,strerror(errno),strpolicy,schedp.sched_priority);
|
||||
}
|
||||
else
|
||||
{
|
||||
client_printf("policy set to %s, priority %i\n",strpolicy,schedp.sched_priority);
|
||||
}
|
||||
|
||||
|
||||
|
||||
if ( policy == SCHED_OTHER)
|
||||
{
|
||||
if ( tid > 0 && tid != pthread_self())
|
||||
{
|
||||
client_printf("setting nice value using a thread id not implemented....\n");
|
||||
}
|
||||
else if (pid > 0)
|
||||
{
|
||||
errno=0;
|
||||
rt = setpriority(PRIO_PROCESS,pid,priority);
|
||||
if (rt != 0)
|
||||
{
|
||||
client_printf("Error %i: %s calling setpriority, \n",errno,strerror(errno));
|
||||
}
|
||||
else
|
||||
{
|
||||
client_printf("nice value set to %i\n",priority);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void set_affinity(pthread_t tid, int pid, int coreid)
|
||||
{
|
||||
cpu_set_t cpuset;
|
||||
int rt;
|
||||
|
||||
CPU_ZERO(&cpuset);
|
||||
CPU_SET(coreid, &cpuset);
|
||||
if (tid > 0)
|
||||
{
|
||||
rt = pthread_setaffinity_np((pthread_t)tid, sizeof(cpu_set_t), &cpuset);
|
||||
}
|
||||
else if (pid > 0)
|
||||
{
|
||||
rt = sched_setaffinity((pid_t)pid, sizeof(cpu_set_t), &cpuset);
|
||||
}
|
||||
if (rt != 0)
|
||||
{
|
||||
client_printf("Error %i: %s calling , xxx_setaffinity...\n",errno,strerror(errno));
|
||||
}
|
||||
else
|
||||
{
|
||||
client_printf("thread %i affinity set to %i\n",(pid==0)?(int)tid:pid,coreid);
|
||||
}
|
||||
}
|
||||
/*------------------------------------------------------------------------------------*/
|
||||
/*
|
||||
function implementing telnet server specific commands, parameters of the
|
||||
telnet_cmdarray table
|
||||
*/
|
||||
|
||||
void redirstd(char *newfname,telnet_printfunc_t prnt )
|
||||
{
|
||||
FILE *fd;
|
||||
fd=freopen(newfname, "w", stdout);
|
||||
if (fd == NULL)
|
||||
{
|
||||
prnt("ERROR: stdout redir to %s error %s",strerror(errno));
|
||||
}
|
||||
fd=freopen(newfname, "w", stderr);
|
||||
if (fd == NULL)
|
||||
{
|
||||
prnt("ERROR: stderr redir to %s error %s",strerror(errno));
|
||||
}
|
||||
}
|
||||
int setoutput(char *buff, int debug, telnet_printfunc_t prnt)
|
||||
{
|
||||
|
||||
char cmds[TELNET_MAX_MSGLENGTH/TELNET_CMD_MAXSIZE][TELNET_CMD_MAXSIZE];
|
||||
char *logfname;
|
||||
char stdout_str[64];
|
||||
|
||||
|
||||
#define LOGFILE "logfile.log"
|
||||
memset(cmds,0,sizeof(cmds));
|
||||
sscanf(buff,"%9s %32s %9s %9s %9s", cmds[0],cmds[1],cmds[2],cmds[3],cmds[4] );
|
||||
if (strncasecmp(cmds[0],"here",4) == 0)
|
||||
{
|
||||
fflush(stdout);
|
||||
sprintf(stdout_str,"/proc/%i/fd/%i",getpid(),telnetparams.new_socket);
|
||||
dup2(telnetparams.new_socket,fileno(stdout));
|
||||
// freopen(stdout_str, "w", stdout);
|
||||
// freopen(stdout_str, "w", stderr);
|
||||
dup2(telnetparams.new_socket,fileno(stderr));
|
||||
prnt("Log output redirected to this terminal (%s)\n",stdout_str);
|
||||
}
|
||||
if (strncasecmp(cmds[0],"file",4) == 0)
|
||||
{
|
||||
if (cmds[1][0] == 0)
|
||||
logfname=LOGFILE;
|
||||
else
|
||||
logfname=cmds[1];
|
||||
fflush(stdout);
|
||||
redirstd(logfname,prnt);
|
||||
|
||||
}
|
||||
if (strncasecmp(cmds[0],"off",3) == 0)
|
||||
{
|
||||
fflush(stdout);
|
||||
redirstd("/dev/tty",prnt);
|
||||
}
|
||||
|
||||
return CMDSTATUS_FOUND;
|
||||
} /* setoutput */
|
||||
|
||||
int setparam(char *buff, int debug, telnet_printfunc_t prnt)
|
||||
{
|
||||
char cmds[TELNET_MAX_MSGLENGTH/TELNET_CMD_MAXSIZE][TELNET_CMD_MAXSIZE];
|
||||
|
||||
|
||||
memset(cmds,0,sizeof(cmds));
|
||||
sscanf(buff,"%9s %9s %9s %9s %9s", cmds[0],cmds[1],cmds[2],cmds[3],cmds[4] );
|
||||
if (strncasecmp(cmds[0],"prio",4) == 0)
|
||||
{
|
||||
pthread_attr_t attr;
|
||||
int prio;
|
||||
prio=(int)strtol(cmds[1],NULL,0);
|
||||
if (errno == ERANGE)
|
||||
return CMDSTATUS_VARNOTFOUND;
|
||||
telnetparams.priority = prio;
|
||||
set_sched(pthread_self(),0,prio);
|
||||
return CMDSTATUS_FOUND;
|
||||
}
|
||||
if (strncasecmp(cmds[0],"aff",3) == 0)
|
||||
{
|
||||
int aff;
|
||||
aff=(int)strtol(cmds[1],NULL,0);
|
||||
if (errno == ERANGE)
|
||||
return CMDSTATUS_VARNOTFOUND;
|
||||
set_affinity(pthread_self(),0,aff);
|
||||
return CMDSTATUS_FOUND;
|
||||
}
|
||||
|
||||
return CMDSTATUS_NOTFOUND;
|
||||
} /* setparam */
|
||||
/*-------------------------------------------------------------------------------------------------------*/
|
||||
/*
|
||||
generic commands available for all modules loaded by the server
|
||||
*/
|
||||
|
||||
int setgetvar(int moduleindex,char getorset,char *params)
|
||||
{
|
||||
int n,i;
|
||||
char varname[TELNET_CMD_MAXSIZE];
|
||||
char varval[TELNET_CMD_MAXSIZE];
|
||||
|
||||
memset(varname,0,sizeof(varname));
|
||||
memset(varval,0,sizeof(varval));
|
||||
n = sscanf(params,"%s %s",varname,varval);
|
||||
for ( i=0 ; telnetparams.CmdParsers[moduleindex].var[i].varvalptr != NULL ; i++)
|
||||
{
|
||||
if ( strncasecmp(telnetparams.CmdParsers[moduleindex].var[i].varname,varname,strlen(telnetparams.CmdParsers[moduleindex].var[i].varname)) == 0)
|
||||
{
|
||||
if (n > 0 && (getorset == 'g' || getorset == 'G'))
|
||||
{
|
||||
client_printf("%s, %s = ", telnetparams.CmdParsers[moduleindex].module,
|
||||
telnetparams.CmdParsers[moduleindex].var[i].varname );
|
||||
switch(telnetparams.CmdParsers[moduleindex].var[i].vartype)
|
||||
{
|
||||
case TELNET_VARTYPE_INT32:
|
||||
client_printf("%i\n",*(int *)(telnetparams.CmdParsers[moduleindex].var[i].varvalptr));
|
||||
break;
|
||||
case TELNET_VARTYPE_INT16:
|
||||
client_printf("%hi\n",*(short *)(telnetparams.CmdParsers[moduleindex].var[i].varvalptr));
|
||||
break;
|
||||
case TELNET_VARTYPE_DOUBLE:
|
||||
client_printf("%g\n",*(double *)(telnetparams.CmdParsers[moduleindex].var[i].varvalptr));
|
||||
break;
|
||||
case TELNET_VARTYPE_PTR:
|
||||
client_printf("0x%08x\n",*((unsigned int *)(telnetparams.CmdParsers[moduleindex].var[i].varvalptr)));
|
||||
break;
|
||||
default:
|
||||
client_printf("unknown type\n");
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (n > 1 && (getorset == 's' || getorset == 'S'))
|
||||
{
|
||||
client_printf("%s, %s set to \n", telnetparams.CmdParsers[moduleindex].module,
|
||||
telnetparams.CmdParsers[moduleindex].var[i].varname);
|
||||
|
||||
switch(telnetparams.CmdParsers[moduleindex].var[i].vartype)
|
||||
{
|
||||
case TELNET_VARTYPE_INT32:
|
||||
*(int *)(telnetparams.CmdParsers[moduleindex].var[i].varvalptr) = (int)strtol(varval,NULL,0);
|
||||
client_printf("%i\n",*(int *)(telnetparams.CmdParsers[moduleindex].var[i].varvalptr));
|
||||
break;
|
||||
case TELNET_VARTYPE_INT16:
|
||||
*(short *)(telnetparams.CmdParsers[moduleindex].var[i].varvalptr) = (short)strtol(varval,NULL,0);
|
||||
client_printf("%hi\n",*(short *)(telnetparams.CmdParsers[moduleindex].var[i].varvalptr));
|
||||
break;
|
||||
case TELNET_VARTYPE_DOUBLE:
|
||||
*(double *)(telnetparams.CmdParsers[moduleindex].var[i].varvalptr) = strtod(varval,NULL);
|
||||
client_printf("%g\n",*(double *)(telnetparams.CmdParsers[moduleindex].var[i].varvalptr));
|
||||
break;
|
||||
default:
|
||||
client_printf("unknown type\n");
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return CMDSTATUS_VARNOTFOUND;
|
||||
}
|
||||
/*----------------------------------------------------------------------------------------------------*/
|
||||
char *get_time(char *buff,int bufflen)
|
||||
{
|
||||
|
||||
struct tm tmstruct;
|
||||
time_t now = time (0);
|
||||
strftime (buff, bufflen, "%Y-%m-%d %H:%M:%S.000", localtime_r(&now,&tmstruct));
|
||||
return buff;
|
||||
}
|
||||
|
||||
int process_command(char *buf)
|
||||
{
|
||||
int i,j,k;
|
||||
char modulename[TELNET_CMD_MAXSIZE];
|
||||
char cmd[TELNET_CMD_MAXSIZE];
|
||||
char cmdb[TELNET_MAX_MSGLENGTH];
|
||||
char *bufbck;
|
||||
int rt;
|
||||
|
||||
memset(modulename,0,sizeof(modulename));
|
||||
memset(cmd,0,sizeof(cmd));
|
||||
memset(cmdb,0,sizeof(cmdb));
|
||||
if (strncasecmp(buf,"ex",2) == 0)
|
||||
return CMDSTATUS_EXIT;
|
||||
|
||||
if (strncasecmp(buf,"help",4) == 0)
|
||||
{
|
||||
for (i=0; telnetparams.CmdParsers[i].var != NULL && telnetparams.CmdParsers[i].cmd != NULL; i++)
|
||||
{
|
||||
client_printf(" module %i = %s:\n",i,telnetparams.CmdParsers[i].module);
|
||||
for(j=0; telnetparams.CmdParsers[i].var[j].varvalptr != NULL ; j++)
|
||||
{
|
||||
client_printf(" %s [get set] %s <value>\n",
|
||||
telnetparams.CmdParsers[i].module, telnetparams.CmdParsers[i].var[j].varname);
|
||||
}
|
||||
for(j=0; telnetparams.CmdParsers[i].cmd[j].cmdfunc != NULL ; j++)
|
||||
{
|
||||
client_printf(" %s %s %s\n",
|
||||
telnetparams.CmdParsers[i].module,telnetparams.CmdParsers[i].cmd[j].cmdname,
|
||||
telnetparams.CmdParsers[i].cmd[j].helpstr);
|
||||
}
|
||||
}
|
||||
return CMDSTATUS_FOUND;
|
||||
}
|
||||
|
||||
memset(modulename,0,sizeof(modulename));
|
||||
memset(cmd,0,sizeof(cmd));
|
||||
memset(cmdb,0,sizeof(cmdb));
|
||||
bufbck=strdup(buf);
|
||||
rt=CMDSTATUS_NOTFOUND;
|
||||
j = sscanf(buf,"%9s %9s %[^\t\n]",modulename,cmd,cmdb);
|
||||
if (telnetparams.telnetdbg > 0)
|
||||
printf("process_command: %i words, module=%s cmd=%s, parameters= %s\n",j,modulename,cmd,cmdb);
|
||||
for (i=0; j>=2 && telnetparams.CmdParsers[i].var != NULL && telnetparams.CmdParsers[i].cmd != NULL; i++)
|
||||
{
|
||||
if ( (strncasecmp(telnetparams.CmdParsers[i].module,modulename,strlen(telnetparams.CmdParsers[i].module)) == 0))
|
||||
{
|
||||
if (strncasecmp(cmd,"getall",7) == 0 )
|
||||
{
|
||||
for(j=0; telnetparams.CmdParsers[i].var[j].varvalptr != NULL ; j++)
|
||||
{
|
||||
setgetvar(i,'g',telnetparams.CmdParsers[i].var[j].varname);
|
||||
}
|
||||
rt= CMDSTATUS_FOUND;
|
||||
}
|
||||
else if (strncasecmp(cmd,"get",3) == 0 || strncasecmp(cmd,"set",3) == 0)
|
||||
{
|
||||
rt= setgetvar(i,cmd[0],cmdb);
|
||||
}
|
||||
else
|
||||
{
|
||||
for (k=0 ; telnetparams.CmdParsers[i].cmd[k].cmdfunc != NULL ; k++)
|
||||
{
|
||||
if (strncasecmp(cmd, telnetparams.CmdParsers[i].cmd[k].cmdname,sizeof(telnetparams.CmdParsers[i].cmd[k].cmdname)) == 0)
|
||||
{
|
||||
telnetparams.CmdParsers[i].cmd[k].cmdfunc(cmdb, telnetparams.telnetdbg, client_printf);
|
||||
rt= CMDSTATUS_FOUND;
|
||||
}
|
||||
} /* for k */
|
||||
}/* else */
|
||||
}/* strncmp: module name test */
|
||||
else if (strncasecmp(modulename,"loop",4) == 0 )
|
||||
{
|
||||
int lc;
|
||||
int f = fcntl(telnetparams.new_socket,F_GETFL);
|
||||
fcntl (telnetparams.new_socket, F_SETFL, O_NONBLOCK | f);
|
||||
for(lc=0; lc<telnetparams.loopcount; lc++)
|
||||
{
|
||||
char dummybuff[20];
|
||||
char tbuff[64];
|
||||
int rs;
|
||||
client_printf(CSI "1J" CSI "1;10H " STDFMT "%s %i/%i\n",
|
||||
get_time(tbuff,sizeof(tbuff)),lc,telnetparams.loopcount );
|
||||
process_command(bufbck+strlen("loop")+1);
|
||||
usleep(telnetparams.loopdelay * 1000);
|
||||
rs = read(telnetparams.new_socket,dummybuff,sizeof(dummybuff));
|
||||
if ( rs > 0 )
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
fcntl (telnetparams.new_socket, F_SETFL, f);
|
||||
rt= CMDSTATUS_FOUND;
|
||||
} /* loop */
|
||||
} /* for i */
|
||||
free(bufbck);
|
||||
return rt;
|
||||
}
|
||||
|
||||
void run_telnetsrv(void)
|
||||
{
|
||||
int sock;
|
||||
struct sockaddr_in name;
|
||||
char buf[TELNET_MAX_MSGLENGTH];
|
||||
struct sockaddr cli_addr;
|
||||
unsigned int cli_len = sizeof(cli_addr);
|
||||
int readc , filled;
|
||||
|
||||
int status;
|
||||
int optval = 1;
|
||||
|
||||
pthread_setname_np(pthread_self(), "telnet");
|
||||
set_sched(pthread_self(),0,telnetparams.priority);
|
||||
sock = socket(AF_INET, SOCK_STREAM, 0);
|
||||
if (sock < 0)
|
||||
fprintf(stderr,"[TELNETSRV] Error %s on socket call\n",strerror(errno));
|
||||
|
||||
setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &optval, sizeof optval);
|
||||
name.sin_family = AF_INET;
|
||||
if (telnetparams.listenaddr == 0)
|
||||
name.sin_addr.s_addr = INADDR_ANY;
|
||||
else
|
||||
name.sin_addr.s_addr = telnetparams.listenaddr;
|
||||
name.sin_port = htons((unsigned short)(telnetparams.listenport));
|
||||
|
||||
if(bind(sock, (void*) &name, sizeof(name)))
|
||||
fprintf(stderr,"[TELNETSRV] Error %s on bind call\n",strerror(errno));
|
||||
if(listen(sock, 1) == -1)
|
||||
fprintf(stderr,"[TELNETSRV] Error %s on listen call\n",strerror(errno));
|
||||
|
||||
|
||||
|
||||
printf("\nInitializing telnet server...\n");
|
||||
while( (telnetparams.new_socket = accept(sock, &cli_addr, &cli_len)) )
|
||||
{
|
||||
printf("[TELNETSRV] Telnet client connected....\n");
|
||||
|
||||
|
||||
if(telnetparams.new_socket < 0)
|
||||
fprintf(stderr,"[TELNETSRV] Error %s on accept call\n",strerror(errno));
|
||||
|
||||
while(telnetparams.new_socket>0)
|
||||
{
|
||||
filled = 0;
|
||||
memset(buf,0,sizeof(buf));
|
||||
while(filled < ( TELNET_MAX_MSGLENGTH-1))
|
||||
{
|
||||
readc = recv(telnetparams.new_socket, buf+filled, TELNET_MAX_MSGLENGTH-filled-1, 0);
|
||||
if(!readc)
|
||||
break;
|
||||
filled += readc;
|
||||
if(buf[filled-1] == '\n')
|
||||
{
|
||||
buf[filled-1] = 0;
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
if(!readc)
|
||||
{
|
||||
printf ("[TELNETSRV] Telnet Client disconnected.\n");
|
||||
break;
|
||||
}
|
||||
if (telnetparams.telnetdbg > 0)
|
||||
printf("[TELNETSRV] Command received: readc %i filled %i %s\n", readc, filled ,buf);
|
||||
if (strlen(buf) >= 2 )
|
||||
{
|
||||
status=process_command(buf);
|
||||
}
|
||||
else
|
||||
status=CMDSTATUS_NOCMD;
|
||||
|
||||
if (status != CMDSTATUS_EXIT)
|
||||
{
|
||||
if (status == CMDSTATUS_NOTFOUND)
|
||||
{
|
||||
char msg[TELNET_MAX_MSGLENGTH + 50];
|
||||
sprintf(msg,"Error: \n %s\n is not a softmodem command\n",buf);
|
||||
send(telnetparams.new_socket, msg, strlen(msg), MSG_NOSIGNAL);
|
||||
}
|
||||
send(telnetparams.new_socket, TELNET_PROMPT, sizeof(TELNET_PROMPT), MSG_NOSIGNAL);
|
||||
}
|
||||
else
|
||||
{
|
||||
printf ("[TELNETSRV] Closing telnet connection...\n");
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
close(telnetparams.new_socket);
|
||||
printf ("[TELNETSRV] Telnet server waitting for connection...\n");
|
||||
}
|
||||
close(sock);
|
||||
return;
|
||||
}
|
||||
|
||||
/*------------------------------------------------------------------------------------------------*/
|
||||
/* set_telnetmodule loads the commands delivered with the telnet server
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
void exec_moduleinit(char *modname)
|
||||
{
|
||||
void (*fptr)();
|
||||
char initfunc[TELNET_CMD_MAXSIZE+9];
|
||||
|
||||
if (strlen(modname) > TELNET_CMD_MAXSIZE)
|
||||
{
|
||||
fprintf(stderr,"[TELNETSRV] module %s not loaded, name exceeds the %i size limit\n",
|
||||
modname, TELNET_CMD_MAXSIZE);
|
||||
return;
|
||||
}
|
||||
sprintf(initfunc,"add_%s_cmds",modname);
|
||||
fptr = dlsym(RTLD_DEFAULT,initfunc);
|
||||
if ( fptr != NULL)
|
||||
{
|
||||
fptr();
|
||||
}
|
||||
else
|
||||
{
|
||||
fprintf(stderr,"[TELNETSRV] couldn't find %s for module %s \n",initfunc,modname);
|
||||
}
|
||||
}
|
||||
|
||||
int add_embeddedmodules()
|
||||
{
|
||||
|
||||
|
||||
|
||||
|
||||
for(int i=0; i<telnetoptions[TELNETSRV_STATICMOD].numelt;i++)
|
||||
{
|
||||
exec_moduleinit(telnetoptions[TELNETSRV_STATICMOD].strlistptr[i]);
|
||||
}
|
||||
}
|
||||
|
||||
int add_sharedmodules()
|
||||
{
|
||||
char initfunc[TELNET_CMD_MAXSIZE+9];
|
||||
void (*fptr)();
|
||||
|
||||
|
||||
for(int i=0; i<telnetoptions[TELNETSRV_SHRMOD].numelt;i++)
|
||||
{
|
||||
sprintf(initfunc,"add_%s_cmds",telnetoptions[TELNETSRV_SHRMOD].strlistptr[i]);
|
||||
fptr = dlsym(RTLD_DEFAULT,initfunc);
|
||||
if ( fptr != NULL)
|
||||
{
|
||||
fptr();
|
||||
}
|
||||
else
|
||||
{
|
||||
fprintf(stderr,"[TELNETSRV] couldn't find %s for module %s \n",initfunc,telnetoptions[TELNETSRV_STATICMOD].strlistptr[i]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int init_telnetsrv(char *cfgfile)
|
||||
{
|
||||
void *lib_handle;
|
||||
char** moduleslist;
|
||||
|
||||
memset(&telnetparams,0,sizeof(telnetparams));
|
||||
|
||||
config_get( telnetoptions,sizeof(telnetoptions)/sizeof(paramdef_t),NULL);
|
||||
|
||||
|
||||
if(pthread_create(&telnetparams.telnet_pthread,NULL, (void *(*)(void *))run_telnetsrv, NULL) != 0)
|
||||
{
|
||||
fprintf(stderr,"[TELNETSRV] Error %s on pthread_create call\n",strerror(errno));
|
||||
return -1;
|
||||
}
|
||||
add_telnetcmd("telnet", telnet_vardef, telnet_cmdarray);
|
||||
add_embeddedmodules();
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------------------------------------------*/
|
||||
/* add_telnetcmd is used to add a set of commands to the telnet server. A module calls this
|
||||
* function at init time. the telnet server is delivered with a set of commands which
|
||||
* will be loaded or not depending on the telnet section of the config file
|
||||
*/
|
||||
int add_telnetcmd(char *modulename, telnetshell_vardef_t *var, telnetshell_cmddef_t *cmd)
|
||||
{
|
||||
int i;
|
||||
if( modulename == NULL || var == NULL || cmd == NULL)
|
||||
{
|
||||
fprintf(stderr,"[TELNETSRV] Telnet server, add_telnetcmd: invalid parameters\n");
|
||||
return -1;
|
||||
}
|
||||
for (i=0; i<TELNET_MAXCMD ; i++)
|
||||
{
|
||||
if (telnetparams.CmdParsers[i].var == NULL)
|
||||
{
|
||||
strncpy(telnetparams.CmdParsers[i].module,modulename,sizeof(telnetparams.CmdParsers[i].module)-1);
|
||||
telnetparams.CmdParsers[i].cmd = cmd;
|
||||
telnetparams.CmdParsers[i].var = var;
|
||||
printf("[TELNETSRV] Telnet server: module %i = %s added to shell\n",
|
||||
i,telnetparams.CmdParsers[i].module);
|
||||
break;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -0,0 +1,108 @@
|
||||
#ifndef TELNETSRV_H
|
||||
#define TELNETSRV_H
|
||||
|
||||
#define TELNETSRV_SHAREDLIB "libtelnetsrv.so"
|
||||
|
||||
#define TELNET_PORT 9090
|
||||
#define TELNET_MAX_MSGLENGTH 2048
|
||||
#define TELNET_PROMPT "softmodem> "
|
||||
#define TELNET_MAXCMD 20
|
||||
#define TELNET_CMD_MAXSIZE 10
|
||||
#define TELNET_HELPSTR_SIZE 80
|
||||
|
||||
/* status return by the command parser after it analysed user input */
|
||||
#define CMDSTATUS_NOCMD 0
|
||||
#define CMDSTATUS_EXIT 1
|
||||
#define CMDSTATUS_FOUND 2
|
||||
#define CMDSTATUS_VARNOTFOUND 3
|
||||
#define CMDSTATUS_NOTFOUND 4
|
||||
|
||||
/*----------------------------------------------------------------------------*/
|
||||
/* structure to be used when adding a module to the telnet server */
|
||||
/* This is the second parameter of the add_telnetcmd function, which can be used */
|
||||
/* to add a set of new command to the telnet server shell */
|
||||
typedef void(*telnet_printfunc_t)(const char* format, ...);
|
||||
typedef int(*cmdfunc_t)(char*, int, telnet_printfunc_t prnt);
|
||||
|
||||
typedef struct cmddef {
|
||||
char cmdname[TELNET_CMD_MAXSIZE];
|
||||
char helpstr[TELNET_HELPSTR_SIZE];
|
||||
cmdfunc_t cmdfunc;
|
||||
} telnetshell_cmddef_t;
|
||||
|
||||
/*----------------------------------------------------------------------------*/
|
||||
/*structure to be used when adding a module to the telnet server */
|
||||
/* This is the first parameter of the add_telnetcmd function, which can be used */
|
||||
/* to add a set of new variables which can be got/set from the telnet server shell */
|
||||
#define TELNET_VARTYPE_INT32 1
|
||||
#define TELNET_VARTYPE_INT16 2
|
||||
#define TELNET_VARTYPE_INT64 3
|
||||
#define TELNET_VARTYPE_STRING 4
|
||||
#define TELNET_VARTYPE_DOUBLE 5
|
||||
#define TELNET_VARTYPE_PTR 6
|
||||
typedef struct variabledef {
|
||||
char varname[TELNET_CMD_MAXSIZE];
|
||||
char vartype;
|
||||
void *varvalptr;
|
||||
} telnetshell_vardef_t;
|
||||
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------------*/
|
||||
/* internal structure definitions */
|
||||
/* cmdparser_t is used to store all modules which have been added to the telnet server. */
|
||||
/* Each time the add_telnetcmd function is used, the internal array cmdparser_t[] of the */
|
||||
/* telnet server is populated with the new commands and variables */
|
||||
typedef struct cmdparser {
|
||||
char module[TELNET_CMD_MAXSIZE]; // module name = first token of the telnet shell command
|
||||
telnetshell_cmddef_t *cmd; // array of functions added to the shell
|
||||
telnetshell_vardef_t *var; // array of variables added to the shell
|
||||
} cmdparser_t;
|
||||
|
||||
/* telnetsrv_params_t is an internal structure storing all the current parameters and */
|
||||
/* global variables used by the telnet server */
|
||||
typedef struct {
|
||||
pthread_t telnet_pthread; // thread id of the telnet server
|
||||
int telnetdbg; // debug level of the server
|
||||
int priority; // server running priority
|
||||
int new_socket; // socket of the client connection
|
||||
int logfilefd; // file id of the log file when log output is redirected to a file
|
||||
int saved_stdout; // file id of the previous stdout, used to be able to restore original stdout
|
||||
cmdparser_t CmdParsers[TELNET_MAXCMD]; // array of registered modules.
|
||||
char msgbuff[TELNET_MAX_MSGLENGTH]; // internal buffer of the client_printf function which is used to print to the client terminal */
|
||||
unsigned int listenport; // ip port the telnet server is listening on
|
||||
unsigned int listenaddr; // ip address the telnet server is listening on
|
||||
unsigned int loopcount; // loop command param: number of loop iteration
|
||||
unsigned int loopdelay; // loop command param: delay in ms between 2 iterations
|
||||
unsigned int phyprntbuff_size; // for phy module, dump_eNB_stats function buffer size
|
||||
} telnetsrv_params_t;
|
||||
|
||||
|
||||
|
||||
typedef int(*addcmdfunc_t)(char*, telnetshell_vardef_t*, telnetshell_cmddef_t*);
|
||||
typedef int(*initfunc_t)(char *cfgfile);
|
||||
typedef void(*settelnetmodule_t)(char *name, void *ptr);
|
||||
|
||||
/*-------------------------------------------------------------------------------------------*/
|
||||
/*
|
||||
VT escape sequence definition, for smarter display....
|
||||
*/
|
||||
|
||||
#define ESC "\x1b"
|
||||
#define CSI "\x1b["
|
||||
#define BOLD "\x1b[1m"
|
||||
#define RED "\x1b[31m"
|
||||
#define GREEN "\x1b[32m"
|
||||
#define BLUE "\x1b[34m"
|
||||
#define MAGENTA "\x1b[35m"
|
||||
#define CYAN "\x1b[36m"
|
||||
#define STDFMT "\x1b[0m"
|
||||
|
||||
/*---------------------------------------------------------------------------------------------*/
|
||||
#ifdef TELNETSERVERCODE
|
||||
int add_telnetcmd(char *modulename, telnetshell_vardef_t *var, telnetshell_cmddef_t *cmd);
|
||||
void set_sched(pthread_t tid, int pid,int priority);
|
||||
void set_affinity(pthread_t tid, int pid, int coreid);
|
||||
extern int get_phybsize();
|
||||
#endif
|
||||
#endif
|
||||
@@ -0,0 +1,134 @@
|
||||
#define _GNU_SOURCE
|
||||
#include <string.h>
|
||||
#include <pthread.h>
|
||||
|
||||
|
||||
#define TELNETSERVERCODE
|
||||
#include "telnetsrv.h"
|
||||
#define TELNETSRV_PHYCMD_MAIN
|
||||
#include "telnetsrv_phycmd.h"
|
||||
char *prnbuff;
|
||||
extern int dump_eNB_stats(PHY_VARS_eNB *eNB, char* buffer, int length);
|
||||
|
||||
void init_phytelnet()
|
||||
{
|
||||
if (PHY_vars_eNB_g != NULL)
|
||||
printf("init_phytelnet: phy var at 0x%08lx\n",(unsigned long int)PHY_vars_eNB_g);
|
||||
else
|
||||
fprintf(stderr,"init_phytelnet: phy var not found...\n");
|
||||
|
||||
|
||||
|
||||
phy_vardef[TELNETVAR_PHYCC0].varvalptr = &(PHY_vars_eNB_g[0][0]);
|
||||
phy_vardef[TELNETVAR_PHYCC1].varvalptr = &(PHY_vars_eNB_g[0][1]);
|
||||
prnbuff=malloc(get_phybsize() );
|
||||
if (prnbuff == NULL)
|
||||
{
|
||||
fprintf(stderr,"Error %s on malloc in init_phytelnet()\n",strerror(errno));
|
||||
}
|
||||
}
|
||||
|
||||
void display_uestatshead( telnet_printfunc_t prnt)
|
||||
{
|
||||
prnt("cc ue rnti Dmcs Umcs tao tau Dbr Dtb \n");
|
||||
}
|
||||
|
||||
void dump_uestats(int debug, telnet_printfunc_t prnt, uint8_t prntflag)
|
||||
{
|
||||
|
||||
int p;
|
||||
|
||||
p=dump_eNB_stats(PHY_vars_eNB_g[0][0], prnbuff, 0);
|
||||
if(prntflag>=1)
|
||||
prnt("%s\n",prnbuff);
|
||||
if(debug>=1)
|
||||
prnt("%i bytes printed\n",p);
|
||||
|
||||
|
||||
}
|
||||
|
||||
void display_uestats(int debug, telnet_printfunc_t prnt, int ue)
|
||||
{
|
||||
for (int cc=0; cc<1 ; cc++)
|
||||
{
|
||||
|
||||
if ((PHY_vars_eNB_g[0][cc]->dlsch[ue][0]->rnti>0)&&
|
||||
(PHY_vars_eNB_g[0][cc]->UE_stats[ue].mode == PUSCH))
|
||||
{
|
||||
prnt("%02i %04i %04hx %04i %04i %04i %-04i %04i %06i\n",cc, ue,
|
||||
PHY_vars_eNB_g[0][cc]->UE_stats[ue].crnti,
|
||||
PHY_vars_eNB_g[0][cc]->dlsch[ue][0]->harq_processes[0]->mcs,0,
|
||||
// PHY_vars_eNB_g[0][cc]->ulsch[ue]->harq_processes[0]->mcs,
|
||||
PHY_vars_eNB_g[0][cc]->UE_stats[ue].UE_timing_offset,
|
||||
PHY_vars_eNB_g[0][cc]->UE_stats[ue].timing_advance_update,
|
||||
PHY_vars_eNB_g[0][cc]->UE_stats[ue].dlsch_bitrate/1000,
|
||||
PHY_vars_eNB_g[0][cc]->UE_stats[ue].total_TBS/1000
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void display_phycounters(char *buf, int debug, telnet_printfunc_t prnt)
|
||||
{
|
||||
prnt(" DLSCH kb DLSCH kb/s\n");
|
||||
|
||||
dump_uestats(debug, prnt,0);
|
||||
prnt(" %09i %06i\n",
|
||||
PHY_vars_eNB_g[0][0]->total_transmitted_bits/1000,
|
||||
PHY_vars_eNB_g[0][0]->total_dlsch_bitrate/1000);
|
||||
}
|
||||
|
||||
int dump_phyvars(char *buf, int debug, telnet_printfunc_t prnt)
|
||||
{
|
||||
|
||||
|
||||
|
||||
if (debug > 0)
|
||||
prnt("phy interface module received %s\n",buf);
|
||||
if (strcasestr(buf,"phycnt") != NULL)
|
||||
{
|
||||
display_phycounters(buf, debug, prnt);
|
||||
}
|
||||
if (strcasestr(buf,"uestat") != NULL)
|
||||
{
|
||||
char *cptr=strcasestr(buf+sizeof("uestat"),"UE");
|
||||
display_uestatshead(prnt);
|
||||
if (cptr != NULL)
|
||||
{
|
||||
int ueidx = strtol( cptr+sizeof("UE"), NULL, 10);
|
||||
if (ueidx < NUMBER_OF_UE_MAX && ueidx >= 0)
|
||||
{
|
||||
display_uestats(debug, prnt,ueidx);
|
||||
}
|
||||
} /* if cptr != NULL */
|
||||
else
|
||||
{
|
||||
for (int ue=0; ue<NUMBER_OF_UE_MAX ; ue++)
|
||||
{
|
||||
display_uestats(debug, prnt,ue);
|
||||
}
|
||||
} /* else cptr != NULL */
|
||||
} /* uestat */
|
||||
if (strcasestr(buf,"uedump") != NULL)
|
||||
{
|
||||
dump_uestats(debug, prnt,1);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
telnetshell_cmddef_t phy_cmdarray[] = {
|
||||
{"disp","[phycnt,uedump,uestat UE<x>]", dump_phyvars},
|
||||
|
||||
{"","",NULL},
|
||||
};
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------------------------*/
|
||||
void add_phy_cmds()
|
||||
{
|
||||
|
||||
init_phytelnet();
|
||||
add_telnetcmd("phy", phy_vardef, phy_cmdarray);
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
|
||||
|
||||
#ifdef TELNETSRV_PHYCMD_MAIN
|
||||
|
||||
#include "UTIL/LOG/log.h"
|
||||
|
||||
#include "openair1/PHY/defs.h"
|
||||
|
||||
|
||||
#define TELNETVAR_PHYCC0 0
|
||||
#define TELNETVAR_PHYCC1 1
|
||||
|
||||
telnetshell_vardef_t phy_vardef[] = {
|
||||
{"phycc1",TELNET_VARTYPE_PTR,NULL},
|
||||
{"phycc2",TELNET_VARTYPE_PTR,NULL},
|
||||
//{"iqmax",TELNET_VARTYPE_INT16,NULL},
|
||||
//{"iqmin",TELNET_VARTYPE_INT16,NULL},
|
||||
//{"loglvl",TELNET_VARTYPE_INT32,NULL},
|
||||
//{"sndslp",TELNET_VARTYPE_INT32,NULL},
|
||||
//{"rxrescale",TELNET_VARTYPE_INT32,NULL},
|
||||
//{"txshift",TELNET_VARTYPE_INT32,NULL},
|
||||
//{"rachemin",TELNET_VARTYPE_INT32,NULL},
|
||||
//{"rachdmax",TELNET_VARTYPE_INT32,NULL},
|
||||
{"",0,NULL}
|
||||
};
|
||||
extern PHY_VARS_eNB ***PHY_vars_eNB_g;
|
||||
#else
|
||||
|
||||
extern void add_phy_cmds();
|
||||
|
||||
#endif
|
||||
|
||||
/*-------------------------------------------------------------------------------------*/
|
||||
|
||||
@@ -0,0 +1,226 @@
|
||||
#define _GNU_SOURCE
|
||||
#include <sys/types.h>
|
||||
#include <sys/socket.h>
|
||||
#include <netinet/in.h>
|
||||
#include <arpa/inet.h>
|
||||
#include <netdb.h>
|
||||
#include <stdio.h>
|
||||
#include <unistd.h>
|
||||
#include <fcntl.h>
|
||||
#include <errno.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <signal.h>
|
||||
#include <pthread.h>
|
||||
#include <string.h>
|
||||
#include <stdarg.h>
|
||||
#include <dirent.h>
|
||||
|
||||
#define READCFG_DYNLOAD
|
||||
|
||||
#define TELNETSERVERCODE
|
||||
#include "telnetsrv.h"
|
||||
#define TELNETSRV_PROCCMD_MAIN
|
||||
#include "log.h"
|
||||
#include "telnetsrv_proccmd.h"
|
||||
|
||||
void decode_procstat(char *record, int debug, telnet_printfunc_t prnt)
|
||||
{
|
||||
char prntline[160];
|
||||
char *procfile_fiels;
|
||||
char *strtokptr;
|
||||
char *lptr;
|
||||
int fieldcnt;
|
||||
char toksep[2];
|
||||
|
||||
fieldcnt=0;
|
||||
procfile_fiels =strtok_r(record," ",&strtokptr);
|
||||
lptr= prntline;
|
||||
/*http://man7.org/linux/man-pages/man5/proc.5.html gives the structure of the stat file */
|
||||
|
||||
while( procfile_fiels != NULL && fieldcnt < 42)
|
||||
{
|
||||
if (strlen(procfile_fiels) == 0)
|
||||
continue;
|
||||
fieldcnt++;
|
||||
sprintf(toksep," ");
|
||||
switch(fieldcnt)
|
||||
{
|
||||
case 1: /* id */
|
||||
lptr+=sprintf(lptr,"%9.9s ",procfile_fiels);
|
||||
sprintf(toksep,")");
|
||||
break;
|
||||
case 2: /* name */
|
||||
lptr+=sprintf(lptr,"%20.20s ",procfile_fiels+1);
|
||||
break;
|
||||
case 3: //thread state
|
||||
lptr+=sprintf(lptr," %c ",procfile_fiels[0]);
|
||||
break;
|
||||
case 14: //time in user mode
|
||||
case 15: //time in kernel mode
|
||||
lptr+=sprintf(lptr,"%9.9s ",procfile_fiels);
|
||||
break;
|
||||
case 18: //priority
|
||||
case 19: //nice
|
||||
lptr+=sprintf(lptr,"%3.3s ",procfile_fiels);
|
||||
break;
|
||||
case 23: //vsize
|
||||
lptr+=sprintf(lptr,"%9.9s ",procfile_fiels);
|
||||
break;
|
||||
case 39: //processor
|
||||
lptr+=sprintf(lptr," %2.2s ",procfile_fiels);
|
||||
break;
|
||||
case 41: //policy
|
||||
lptr+=sprintf(lptr,"%3.3s ",procfile_fiels);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}/* switch on fieldcnr */
|
||||
procfile_fiels =strtok_r(NULL,toksep,&strtokptr);
|
||||
} /* while on proc_fields != NULL */
|
||||
prnt("%s\n",prntline);
|
||||
} /*decode_procstat */
|
||||
|
||||
void read_statfile(char *fname,int debug, telnet_printfunc_t prnt)
|
||||
{
|
||||
FILE *procfile;
|
||||
char arecord[1024];
|
||||
|
||||
procfile=fopen(fname,"r");
|
||||
if (procfile == NULL)
|
||||
{
|
||||
prnt("Error: Couldn't open %s %i %s\n",fname,errno,strerror(errno));
|
||||
return;
|
||||
}
|
||||
if ( fgets(arecord,sizeof(arecord),procfile) == NULL)
|
||||
{
|
||||
prnt("Error: Nothing read from %s %i %s\n",fname,errno,strerror(errno));
|
||||
fclose(procfile);
|
||||
return;
|
||||
}
|
||||
fclose(procfile);
|
||||
decode_procstat(arecord, debug, prnt);
|
||||
}
|
||||
|
||||
void print_threads(char *buf, int debug, telnet_printfunc_t prnt)
|
||||
{
|
||||
char aname[256];
|
||||
|
||||
DIR *proc_dir;
|
||||
struct dirent *entry;
|
||||
|
||||
int rt;
|
||||
|
||||
prnt(" id name state USRmod KRNmod prio nice vsize proc pol \n\n");
|
||||
snprintf(aname, sizeof(aname), "/proc/%d/stat", getpid());
|
||||
read_statfile(aname,debug,prnt);
|
||||
prnt("\n");
|
||||
snprintf(aname, sizeof(aname), "/proc/%d/task", getpid());
|
||||
proc_dir = opendir(aname);
|
||||
if (proc_dir == NULL)
|
||||
{
|
||||
prnt("Error: Couldn't open %s %i %s\n",aname,errno,strerror(errno));
|
||||
return;
|
||||
}
|
||||
|
||||
while ((entry = readdir(proc_dir)) != NULL)
|
||||
{
|
||||
if(entry->d_name[0] == '.')
|
||||
continue;
|
||||
snprintf(aname, sizeof(aname), "/proc/%d/task/%s/stat", getpid(),entry->d_name);
|
||||
read_statfile(aname,debug,prnt);
|
||||
} /* while entry != NULL */
|
||||
closedir(proc_dir);
|
||||
} /* print_threads */
|
||||
|
||||
|
||||
int proccmd_show(char *buf, int debug, telnet_printfunc_t prnt)
|
||||
{
|
||||
extern log_t *g_log;
|
||||
|
||||
if (debug > 0)
|
||||
prnt(" proccmd_show received %s\n",buf);
|
||||
if (strcasestr(buf,"thread") != NULL)
|
||||
{
|
||||
print_threads(buf,debug,prnt);
|
||||
}
|
||||
if (strcasestr(buf,"loglvl") != NULL) {
|
||||
for (int i=MIN_LOG_COMPONENTS; i < MAX_LOG_COMPONENTS; i++){
|
||||
prnt("\t%s:\t%s\t%s\n",g_log->log_component[i].name, map_int_to_str(log_verbosity_names,g_log->log_component[i].flag),
|
||||
map_int_to_str(log_level_names,g_log->log_component[i].level));
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int proccmd_thread(char *buf, int debug, telnet_printfunc_t prnt)
|
||||
{
|
||||
int bv1,bv2;
|
||||
int res;
|
||||
char sv1[64];
|
||||
char tname[32];
|
||||
bv1=0;
|
||||
bv2=0;
|
||||
sv1[0]=0;
|
||||
if (debug > 0)
|
||||
prnt("proccmd_thread received %s\n",buf);
|
||||
res=sscanf(buf,"%i %9s %i",&bv1,sv1,&bv2);
|
||||
if (debug > 0)
|
||||
prnt(" proccmd_thread: %i params = %i,%s,%i\n",res,bv1,sv1,bv2);
|
||||
if(res != 3)
|
||||
{
|
||||
prnt("softmodem thread needs 3 params, %i received\n",res);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
if (strcasestr(sv1,"prio") != NULL)
|
||||
{
|
||||
set_sched(0,bv1, bv2);
|
||||
}
|
||||
else if (strcasestr(sv1,"aff") != NULL)
|
||||
{
|
||||
set_affinity(0,bv1, bv2);
|
||||
}
|
||||
else
|
||||
{
|
||||
prnt("%s is not a valid thread command\n",sv1);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
int proccmd_exit(char *buf, int debug, telnet_printfunc_t prnt)
|
||||
{
|
||||
extern void exit_fun(const char* s);
|
||||
|
||||
if (debug > 0)
|
||||
prnt("process module received %s\n",buf);
|
||||
|
||||
exit_fun("telnet server received exit command\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
int proccmd_log(char *buf, int debug, telnet_printfunc_t prnt)
|
||||
{
|
||||
int idx1=0;
|
||||
int idx2=NUM_LOG_LEVEL-1;
|
||||
int s = sscanf(buf,"%*s %i-%i",&idx1,&idx2);
|
||||
|
||||
if (debug > 0)
|
||||
prnt("process module received %s\n",buf);
|
||||
|
||||
if (strcasestr(buf,"enable") != NULL)
|
||||
{
|
||||
set_glog_onlinelog(1);
|
||||
}
|
||||
if (strcasestr(buf,"disable") != NULL)
|
||||
{
|
||||
set_glog_onlinelog(0);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
/*-------------------------------------------------------------------------------------*/
|
||||
|
||||
void add_softmodem_cmds()
|
||||
{
|
||||
add_telnetcmd("softmodem",NULL,proc_cmdarray);
|
||||
}
|
||||
@@ -0,0 +1,56 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file common/utils/telnetsrv_proccmd.h
|
||||
* \brief: Include file defining telnet commands related to this linux process
|
||||
* \author Francois TABURET
|
||||
* \date 2017
|
||||
* \version 0.1
|
||||
* \company NOKIA BellLabs France
|
||||
* \email: francois.taburet@nokia-bell-labs.com
|
||||
* \note
|
||||
* \warning
|
||||
*/
|
||||
#include <dlfcn.h>
|
||||
#include "telnetsrv.h"
|
||||
|
||||
|
||||
#ifdef TELNETSRV_PROCCMD_MAIN
|
||||
/* global variable from log.c */
|
||||
extern mapping *log_level_names;
|
||||
extern mapping *log_verbosity_names;
|
||||
|
||||
extern int proccmd_show(char *buf, int debug, telnet_printfunc_t prnt);
|
||||
extern int proccmd_thread(char *buf, int debug, telnet_printfunc_t prnt);
|
||||
extern int proccmd_exit(char *buf, int debug, telnet_printfunc_t prnt);
|
||||
extern int proccmd_log(char *buf, int debug, telnet_printfunc_t prnt);
|
||||
|
||||
telnetshell_cmddef_t proc_cmdarray[] = {
|
||||
{"show","loglvl|thread", proccmd_show},
|
||||
{"log","[enable,disable]", proccmd_log},
|
||||
{"thread","<id> aff|prio <aff|prio>", proccmd_thread},
|
||||
{"exit","", proccmd_exit},
|
||||
{"","",NULL},
|
||||
};
|
||||
#else
|
||||
extern void add_proccmd_cmds();
|
||||
#endif /* TELNETSRV_PROCCMD_MAIN */
|
||||
|
||||
@@ -2439,7 +2439,7 @@ uint32_t rx_pucch(PHY_VARS_eNB *eNB,
|
||||
*payload = (stat_re<0) ? 1 : 2; // 1 == ACK, 2 == NAK
|
||||
|
||||
if (fmt==pucch_format1b)
|
||||
*(1+payload) = (stat_im<0) ? 1 : 0;
|
||||
*(1+payload) = (stat_im<0) ? 1 : 2;
|
||||
} else { // insufficient energy on PUCCH so NAK
|
||||
LOG_D(PHY,"PUCCH 1a/b: subframe %d : sigma2_dB %d, stat_max %d, pucch1_thres %d\n",subframe,sigma2_dB,dB_fixed(stat_max),pucch1_thres);
|
||||
*payload = 4; // DTX
|
||||
@@ -2448,7 +2448,7 @@ uint32_t rx_pucch(PHY_VARS_eNB *eNB,
|
||||
eNB->pucch1ab_stats_cnt[UE_id][subframe] = (eNB->pucch1ab_stats_cnt[UE_id][subframe]+1)&1023;
|
||||
|
||||
if (fmt==pucch_format1b)
|
||||
*(1+payload) = 6;
|
||||
*(1+payload) = 4;
|
||||
}
|
||||
} else {
|
||||
LOG_E(PHY,"[eNB] PUCCH fmt2/2a/2b not supported\n");
|
||||
|
||||
@@ -56,8 +56,8 @@
|
||||
#include "common/config/config_userapi.h"
|
||||
|
||||
|
||||
RCconfig_RRC(MessageDef *msg_p, uint32_t i, eNB_RRC_INST *rrc);
|
||||
RCconfig_S1(MessageDef *msg_p, uint32_t i);
|
||||
int RCconfig_RRC(MessageDef *msg_p, uint32_t i, eNB_RRC_INST *rrc);
|
||||
int RCconfig_S1(MessageDef *msg_p, uint32_t i);
|
||||
|
||||
|
||||
static int enb_check_band_frequencies(char* lib_config_file_name_pP,
|
||||
|
||||
@@ -51,28 +51,7 @@
|
||||
#define ENB_CONF_STRING_OTG_APP_TYPE "app_type"
|
||||
#define ENB_CONF_STRING_OTG_BG_TRAFFIC "bg_traffic"
|
||||
|
||||
// per eNB configuration
|
||||
#define ENB_CONFIG_STRING_LOG_CONFIG "log_config"
|
||||
#define ENB_CONFIG_STRING_GLOBAL_LOG_LEVEL "global_log_level"
|
||||
#define ENB_CONFIG_STRING_GLOBAL_LOG_VERBOSITY "global_log_verbosity"
|
||||
#define ENB_CONFIG_STRING_HW_LOG_LEVEL "hw_log_level"
|
||||
#define ENB_CONFIG_STRING_HW_LOG_VERBOSITY "hw_log_verbosity"
|
||||
#define ENB_CONFIG_STRING_PHY_LOG_LEVEL "phy_log_level"
|
||||
#define ENB_CONFIG_STRING_PHY_LOG_VERBOSITY "phy_log_verbosity"
|
||||
#define ENB_CONFIG_STRING_MAC_LOG_LEVEL "mac_log_level"
|
||||
#define ENB_CONFIG_STRING_MAC_LOG_VERBOSITY "mac_log_verbosity"
|
||||
#define ENB_CONFIG_STRING_RLC_LOG_LEVEL "rlc_log_level"
|
||||
#define ENB_CONFIG_STRING_RLC_LOG_VERBOSITY "rlc_log_verbosity"
|
||||
#define ENB_CONFIG_STRING_PDCP_LOG_LEVEL "pdcp_log_level"
|
||||
#define ENB_CONFIG_STRING_PDCP_LOG_VERBOSITY "pdcp_log_verbosity"
|
||||
#define ENB_CONFIG_STRING_RRC_LOG_LEVEL "rrc_log_level"
|
||||
#define ENB_CONFIG_STRING_RRC_LOG_VERBOSITY "rrc_log_verbosity"
|
||||
#define ENB_CONFIG_STRING_GTPU_LOG_LEVEL "gtpu_log_level"
|
||||
#define ENB_CONFIG_STRING_GTPU_LOG_VERBOSITY "gtpu_log_verbosity"
|
||||
#define ENB_CONFIG_STRING_UDP_LOG_LEVEL "udp_log_level"
|
||||
#define ENB_CONFIG_STRING_UDP_LOG_VERBOSITY "udp_log_verbosity"
|
||||
#define ENB_CONFIG_STRING_OSA_LOG_LEVEL "osa_log_level"
|
||||
#define ENB_CONFIG_STRING_OSA_LOG_VERBOSITY "osa_log_verbosity"
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1276,7 +1276,7 @@ schedule_ue_spec(
|
||||
(frameP*10)+subframeP,
|
||||
TBS,
|
||||
&eNB->pdu_index[CC_id],
|
||||
eNB->UE_list.DLSCH_pdu[CC_id][0][(unsigned char)UE_id].payload[harq_pid]);
|
||||
eNB->UE_list.DLSCH_pdu[CC_id][0][(unsigned char)UE_id].payload[0]);
|
||||
|
||||
LOG_D(MAC,"Filled NFAPI configuration for DCI/DLSCH/TXREQ %d, new SDU\n",eNB->pdu_index[CC_id]);
|
||||
|
||||
|
||||
@@ -3094,14 +3094,15 @@ void extract_harq(module_id_t mod_idP,int CC_idP,int UE_id,frame_t frameP,sub_fr
|
||||
// single ACK/NAK bit
|
||||
AssertFatal(num_ack_nak==1,"num_ack_nak %d > 1 for 1 CC and single-layer transmission\n",num_ack_nak);
|
||||
AssertFatal(sched_ctl->round[CC_idP][harq_pid]<8,"Got ACK/NAK for inactive harq_pid %d for UE %d/%x\n",harq_pid,UE_id,rnti);
|
||||
AssertFatal(pdu[0] == 1 || pdu[0] == 2, "Received ACK/NAK %d which is not 1 or 2 for harq_pid %d from UE %d/%x\n",pdu[0],harq_pid,UE_id,rnti);
|
||||
AssertFatal(pdu[0] == 1 || pdu[0] == 2 || pdu[0] == 4,
|
||||
"Received ACK/NAK %d which is not 1 or 2 for harq_pid %d from UE %d/%x\n",pdu[0],harq_pid,UE_id,rnti);
|
||||
LOG_D(MAC,"Received %d for harq_pid %d\n",pdu[0],harq_pid);
|
||||
|
||||
if (pdu[0] == 1) { // ACK
|
||||
sched_ctl->round[CC_idP][harq_pid]=8; // release HARQ process
|
||||
sched_ctl->tbcnt[CC_idP][harq_pid]=0;
|
||||
}
|
||||
else if (pdu[0] == 2) // NAK
|
||||
else if (pdu[0] == 2 || pdu[0] == 4) // NAK (treat DTX as NAK)
|
||||
sched_ctl->round[CC_idP][harq_pid]++; // increment round
|
||||
}
|
||||
else {
|
||||
|
||||
@@ -596,7 +596,7 @@ void dlsch_scheduler_pre_processor (module_id_t Mod_id,
|
||||
average_rbs_per_user[CC_id]=0;
|
||||
|
||||
|
||||
if(round>0) {
|
||||
if(round != 8) {
|
||||
nb_rbs_required[CC_id][UE_id] = UE_list->UE_template[CC_id][UE_id].nb_rb[harq_pid];
|
||||
}
|
||||
|
||||
|
||||
+60
-5
@@ -33,7 +33,7 @@
|
||||
|
||||
#define COMPONENT_LOG
|
||||
#define COMPONENT_LOG_IF
|
||||
|
||||
#include <ctype.h>
|
||||
#include "log.h"
|
||||
#include "vcd_signal_dumper.h"
|
||||
#include "assertions.h"
|
||||
@@ -53,7 +53,7 @@
|
||||
# define FIFO_PRINTF_NO 62
|
||||
# define FIFO_PRINTF_SIZE 65536
|
||||
#endif
|
||||
|
||||
#include "common/config/config_userapi.h"
|
||||
// main log variables
|
||||
log_t *g_log;
|
||||
|
||||
@@ -103,6 +103,61 @@ static char *log_level_highlight_end[] = {LOG_RESET, LOG_RESET, LOG_RESET, LOG
|
||||
static log_instance_type_t log_instance_type;
|
||||
#endif
|
||||
|
||||
/* get log parameters from configuration file */
|
||||
void log_getconfig(log_t *g_log) {
|
||||
char *gloglevel = NULL;
|
||||
char *glogverbo = NULL;
|
||||
int level,verbosity;
|
||||
paramdef_t logparams_defaults[] = LOG_GLOBALPARAMS_DESC;
|
||||
paramdef_t logparams_level[MAX_LOG_COMPONENTS];
|
||||
paramdef_t logparams_verbosity[MAX_LOG_COMPONENTS];
|
||||
paramdef_t logparams_logfile[MAX_LOG_COMPONENTS];
|
||||
|
||||
config_get( logparams_defaults,sizeof(logparams_defaults)/sizeof(paramdef_t),CONFIG_STRING_LOG_PREFIX);
|
||||
memset(logparams_level, 0, sizeof(paramdef_t)*MAX_LOG_COMPONENTS);
|
||||
memset(logparams_verbosity,0, sizeof(paramdef_t)*MAX_LOG_COMPONENTS);
|
||||
memset(logparams_logfile, 0, sizeof(paramdef_t)*MAX_LOG_COMPONENTS);
|
||||
for (int i=MIN_LOG_COMPONENTS; i < MAX_LOG_COMPONENTS; i++) {
|
||||
if(g_log->log_component[i].name == NULL) {
|
||||
g_log->log_component[i].name = malloc(16);
|
||||
sprintf((char *)g_log->log_component[i].name,"comp%i?",i);
|
||||
logparams_logfile[i].paramflags = PARAMFLAG_DONOTREAD;
|
||||
logparams_level[i].paramflags = PARAMFLAG_DONOTREAD;
|
||||
logparams_verbosity[i].paramflags = PARAMFLAG_DONOTREAD;
|
||||
}
|
||||
sprintf(logparams_level[i].optname, LOG_CONFIG_LEVEL_FORMAT, g_log->log_component[i].name);
|
||||
sprintf(logparams_verbosity[i].optname,LOG_CONFIG_VERBOSITY_FORMAT, g_log->log_component[i].name);
|
||||
sprintf(logparams_logfile[i].optname, LOG_CONFIG_LOGFILE_FORMAT, g_log->log_component[i].name);
|
||||
/* workaround: all log options in existing configuration files use lower case component names
|
||||
where component names include uppercase char in log.h.... */
|
||||
for (int j=0 ; j<strlen(logparams_level[i].optname); j++)
|
||||
logparams_level[i].optname[j] = tolower(logparams_level[i].optname[j]);
|
||||
for (int j=0 ; j<strlen(logparams_level[i].optname); j++)
|
||||
logparams_verbosity[i].optname[j] = tolower(logparams_verbosity[i].optname[j]);
|
||||
for (int j=0 ; j<strlen(logparams_level[i].optname); j++)
|
||||
logparams_logfile[i].optname[j] = tolower(logparams_logfile[i].optname[j]);
|
||||
/* */
|
||||
logparams_level[i].defstrval = gloglevel;
|
||||
logparams_verbosity[i].defstrval = glogverbo;
|
||||
|
||||
logparams_level[i].type = TYPE_STRING;
|
||||
logparams_verbosity[i].type = TYPE_STRING;
|
||||
logparams_logfile[i].type = TYPE_UINT;
|
||||
|
||||
logparams_logfile[i].paramflags = logparams_logfile[i].paramflags|PARAMFLAG_BOOL;
|
||||
}
|
||||
config_get( logparams_level, MAX_LOG_COMPONENTS,CONFIG_STRING_LOG_PREFIX);
|
||||
config_get( logparams_verbosity,MAX_LOG_COMPONENTS,CONFIG_STRING_LOG_PREFIX);
|
||||
config_get( logparams_logfile, MAX_LOG_COMPONENTS,CONFIG_STRING_LOG_PREFIX);
|
||||
for (int i=MIN_LOG_COMPONENTS; i < MAX_LOG_COMPONENTS; i++) {
|
||||
verbosity = map_str_to_int(log_verbosity_names,*(logparams_verbosity[i].strptr));
|
||||
level = map_str_to_int(log_level_names, *(logparams_level[i].strptr));
|
||||
set_comp_log(i, level,verbosity,1);
|
||||
set_component_filelog(*(logparams_logfile[i].uptr));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
int logInit (void)
|
||||
{
|
||||
#ifdef USER_MODE
|
||||
@@ -441,7 +496,7 @@ int logInit (void)
|
||||
openlog(g_log->log_component[EMU].name, LOG_PID, g_log->config.facility);
|
||||
#endif // ! defined(CN_BUILD)
|
||||
}
|
||||
|
||||
log_getconfig(g_log);
|
||||
if (g_log->filelog) {
|
||||
gfd = open(g_log->filelog_name, O_WRONLY | O_CREAT, 0666);
|
||||
}
|
||||
@@ -1319,8 +1374,8 @@ int set_comp_log(int component, int level, int verbosity, int interval)
|
||||
|
||||
void set_glog(int level, int verbosity)
|
||||
{
|
||||
g_log->level = level;
|
||||
g_log->flag = verbosity;
|
||||
if( g_log->level >= 0) g_log->level = level;
|
||||
if( g_log->flag >= 0) g_log->flag = verbosity;
|
||||
}
|
||||
void set_glog_syslog(int enable)
|
||||
{
|
||||
|
||||
+24
-2
@@ -268,8 +268,9 @@ int set_comp_log(int component, int level, int verbosity, int interval);
|
||||
int set_log(int component, int level, int interval);
|
||||
void set_glog(int level, int verbosity);
|
||||
void set_log_syslog(int enable);
|
||||
void set_log_onlinelog(int enable);
|
||||
void set_log_filelog(int enable);
|
||||
void set_glog_onlinelog(int enable);
|
||||
void set_glog_filelog(int enable);
|
||||
|
||||
void set_component_filelog(int comp);
|
||||
int map_str_to_int(mapping *map, const char *str);
|
||||
char *map_int_to_str(mapping *map, int val);
|
||||
@@ -297,7 +298,28 @@ void *log_thread_function(void * list);
|
||||
#endif
|
||||
/* @}*/
|
||||
|
||||
/*----------------macro definitions for reading log configuration from the config module */
|
||||
#define CONFIG_STRING_LOG_PREFIX "log_config"
|
||||
|
||||
#define LOG_CONFIG_STRING_GLOBAL_LOG_LEVEL "global_log_level"
|
||||
#define LOG_CONFIG_STRING_GLOBAL_LOG_VERBOSITY "global_log_verbosity"
|
||||
#define LOG_CONFIG_STRING_GLOBAL_LOG_ONLINE "global_log_online"
|
||||
#define LOG_CONFIG_STRING_GLOBAL_LOG_INFILE "global_log_infile"
|
||||
|
||||
#define LOG_CONFIG_LEVEL_FORMAT "%s_log_level"
|
||||
#define LOG_CONFIG_VERBOSITY_FORMAT "%s_log_verbosity"
|
||||
#define LOG_CONFIG_LOGFILE_FORMAT "%s_log_infile"
|
||||
/*--------------------------------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
/* LOG globalconfiguration parameters */
|
||||
/* optname helpstr paramflags XXXptr defXXXval type numelt */
|
||||
/*--------------------------------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
#define LOG_GLOBALPARAMS_DESC { \
|
||||
{LOG_CONFIG_STRING_GLOBAL_LOG_LEVEL, NULL, 0, strptr:(char **)&gloglevel, defstrval:log_level_names[2].name, TYPE_STRING, sizeof(gloglevel)}, \
|
||||
{LOG_CONFIG_STRING_GLOBAL_LOG_VERBOSITY,NULL, 0, strptr:(char **)&glogverbo, defstrval:log_verbosity_names[2].name, TYPE_STRING, sizeof(glogverbo)}, \
|
||||
{LOG_CONFIG_STRING_GLOBAL_LOG_ONLINE, NULL, 0, iptr:&(g_log->onlinelog), defintval:1, TYPE_INT, 0, }, \
|
||||
{LOG_CONFIG_STRING_GLOBAL_LOG_INFILE, NULL, 0, iptr:&(g_log->filelog), defintval:0, TYPE_INT, 0, }, \
|
||||
}
|
||||
/*----------------------------------------------------------------------------------*/
|
||||
/** @defgroup _debugging debugging macros
|
||||
* @ingroup _macro
|
||||
* @brief Macro used to call logIt function with different message levels
|
||||
|
||||
@@ -99,7 +99,7 @@ void udp_eNB_receiver(struct udp_socket_desc_s *udp_sock_pP);
|
||||
|
||||
void *udp_eNB_task(void *args_p);
|
||||
|
||||
int udp_enb_init();
|
||||
int udp_enb_init(void);
|
||||
/* @brief Retrieve the descriptor associated with the task_id
|
||||
*/
|
||||
static
|
||||
|
||||
@@ -93,6 +93,6 @@ void *udp_eNB_task(void *args_p);
|
||||
* \param enb_config_p configuration of eNB
|
||||
* @returns always 0
|
||||
*/
|
||||
int udp_enb_init();
|
||||
int udp_enb_init(void);
|
||||
|
||||
#endif /* UDP_ENB_TASK_H_ */
|
||||
|
||||
@@ -50,7 +50,7 @@
|
||||
#include "PHY/defs.h"
|
||||
#include "common/ran_context.h"
|
||||
#include "common/config/config_userapi.h"
|
||||
|
||||
#include "common/utils/telnetsrv/load_telnet.h"
|
||||
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
|
||||
//#undef FRAME_LENGTH_COMPLEX_SAMPLES //there are two conflicting definitions, so we better make sure we don't use it at all
|
||||
|
||||
@@ -184,7 +184,7 @@ char ref[128] = "internal";
|
||||
char channels[128] = "0";
|
||||
|
||||
int rx_input_level_dBm;
|
||||
static int online_log_messages=0;
|
||||
|
||||
#ifdef XFORMS
|
||||
extern int otg_enabled;
|
||||
static char do_forms=0;
|
||||
@@ -207,33 +207,7 @@ extern void print_opp_meas(void);
|
||||
|
||||
int transmission_mode=1;
|
||||
|
||||
int16_t glog_level = LOG_INFO;
|
||||
int16_t glog_verbosity = LOG_MED;
|
||||
int16_t hw_log_level = LOG_INFO;
|
||||
int16_t hw_log_verbosity = LOG_MED;
|
||||
int16_t phy_log_level = LOG_DEBUG;
|
||||
int16_t phy_log_verbosity = LOG_MED;
|
||||
int16_t mac_log_level = LOG_DEBUG;
|
||||
int16_t mac_log_verbosity = LOG_MED;
|
||||
int16_t rlc_log_level = LOG_INFO;
|
||||
int16_t rlc_log_verbosity = LOG_MED;
|
||||
int16_t pdcp_log_level = LOG_INFO;
|
||||
int16_t pdcp_log_verbosity = LOG_MED;
|
||||
int16_t rrc_log_level = LOG_INFO;
|
||||
int16_t rrc_log_verbosity = LOG_MED;
|
||||
int16_t opt_log_level = LOG_INFO;
|
||||
int16_t opt_log_verbosity = LOG_MED;
|
||||
|
||||
# if defined(ENABLE_USE_MME)
|
||||
int16_t gtpu_log_level = LOG_DEBUG;
|
||||
int16_t gtpu_log_verbosity = LOG_MED;
|
||||
int16_t udp_log_level = LOG_DEBUG;
|
||||
int16_t udp_log_verbosity = LOG_MED;
|
||||
#endif
|
||||
#if defined (ENABLE_SECURITY)
|
||||
int16_t osa_log_level = LOG_INFO;
|
||||
int16_t osa_log_verbosity = LOG_MED;
|
||||
#endif
|
||||
|
||||
/* struct for ethernet specific parameters given in eNB conf file */
|
||||
eth_params_t *eth_params;
|
||||
@@ -583,7 +557,11 @@ static void get_options(void) {
|
||||
int tddflag;
|
||||
char *loopfile=NULL;
|
||||
int dumpframe;
|
||||
uint32_t online_log_messages;
|
||||
uint32_t glog_level, glog_verbosity;
|
||||
|
||||
paramdef_t cmdline_params[] =CMDLINE_PARAMS_DESC ;
|
||||
paramdef_t cmdline_logparams[] =CMDLINE_LOGPARAMS_DESC ;
|
||||
|
||||
config_process_cmdline( cmdline_params,sizeof(cmdline_params)/sizeof(paramdef_t),NULL);
|
||||
|
||||
@@ -597,6 +575,18 @@ static void get_options(void) {
|
||||
opt_type = OPT_WIRESHARK;
|
||||
printf("Enabling OPT for wireshark for local interface");
|
||||
}
|
||||
|
||||
config_process_cmdline( cmdline_logparams,sizeof(cmdline_logparams)/sizeof(paramdef_t),NULL);
|
||||
if(config_isparamset(cmdline_logparams,CMDLINE_ONLINELOG_IDX)) {
|
||||
set_glog_onlinelog(online_log_messages);
|
||||
}
|
||||
if(config_isparamset(cmdline_logparams,CMDLINE_GLOGLEVEL_IDX)) {
|
||||
set_glog(glog_level, -1);
|
||||
}
|
||||
if(config_isparamset(cmdline_logparams,CMDLINE_GLOGLEVEL_IDX)) {
|
||||
set_glog(-1, glog_verbosity);
|
||||
}
|
||||
|
||||
if (UE_flag > 0) {
|
||||
paramdef_t cmdline_uemodeparams[] =CMDLINE_UEMODEPARAMS_DESC;
|
||||
paramdef_t cmdline_ueparams[] =CMDLINE_UEPARAMS_DESC;
|
||||
@@ -930,8 +920,7 @@ int main( int argc, char **argv )
|
||||
T_init(T_port, T_wait, T_dont_fork);
|
||||
#endif
|
||||
|
||||
// initialize the log (see log.h for details)
|
||||
set_glog(glog_level, glog_verbosity);
|
||||
|
||||
|
||||
//randominit (0);
|
||||
set_taus_seed (0);
|
||||
@@ -956,37 +945,6 @@ int main( int argc, char **argv )
|
||||
} else {
|
||||
printf("configuring for RAU/RRU\n");
|
||||
|
||||
set_comp_log(HW, hw_log_level, hw_log_verbosity, 1);
|
||||
set_comp_log(PHY, phy_log_level, phy_log_verbosity, 1);
|
||||
if (opt_enabled == 1 )
|
||||
set_comp_log(OPT, opt_log_level, opt_log_verbosity, 1);
|
||||
set_comp_log(MAC, mac_log_level, mac_log_verbosity, 1);
|
||||
set_comp_log(RLC, rlc_log_level, rlc_log_verbosity, 1);
|
||||
set_comp_log(PDCP, pdcp_log_level, pdcp_log_verbosity, 1);
|
||||
set_comp_log(RRC, rrc_log_level, rrc_log_verbosity, 1);
|
||||
#if defined(ENABLE_ITTI)
|
||||
set_comp_log(EMU, LOG_INFO, LOG_MED, 1);
|
||||
# if defined(ENABLE_USE_MME)
|
||||
set_comp_log(UDP_, udp_log_level, udp_log_verbosity, 1);
|
||||
set_comp_log(GTPU, gtpu_log_level, gtpu_log_verbosity, 1);
|
||||
set_comp_log(S1AP, LOG_DEBUG, LOG_HIGH, 1);
|
||||
set_comp_log(SCTP, LOG_INFO, LOG_HIGH, 1);
|
||||
# endif
|
||||
#if defined(ENABLE_SECURITY)
|
||||
set_comp_log(OSA, osa_log_level, osa_log_verbosity, 1);
|
||||
#endif
|
||||
#endif
|
||||
#ifdef LOCALIZATION
|
||||
set_comp_log(LOCALIZE, LOG_DEBUG, LOG_LOW, 1);
|
||||
set_component_filelog(LOCALIZE);
|
||||
#endif
|
||||
set_comp_log(ENB_APP, LOG_INFO, LOG_HIGH, 1);
|
||||
set_comp_log(OTG, LOG_INFO, LOG_HIGH, 1);
|
||||
|
||||
if (online_log_messages == 1) {
|
||||
set_component_filelog(RRC);
|
||||
set_component_filelog(PDCP);
|
||||
}
|
||||
}
|
||||
|
||||
if (ouput_vcd) {
|
||||
@@ -1166,7 +1124,7 @@ int main( int argc, char **argv )
|
||||
LOG_I(HW, "CPU Affinity of main() function is... %s\n", cpu_affinity);
|
||||
#endif
|
||||
|
||||
openair0_cfg[0].log_level = glog_level;
|
||||
|
||||
|
||||
|
||||
#if defined(ENABLE_ITTI)
|
||||
|
||||
@@ -68,8 +68,6 @@
|
||||
#define CONFIG_HLP_CHOFF "Channel id offset"
|
||||
#define CONFIG_HLP_SOFTS "Enable soft scope and L1 and L2 stats (Xforms)\n"
|
||||
#define CONFIG_HLP_EXMCAL "Calibrate the EXMIMO borad, available files: exmimo2_2arxg.lime exmimo2_2brxg.lime \n"
|
||||
#define CONFIG_HLP_LOGL "Set the global log level, valide options: (9:trace, 8/7:debug, 6:info, 4:warn, 3:error)\n"
|
||||
#define CONFIG_HLP_LOGV "Set the global log verbosity \n"
|
||||
#define CONFIG_HLP_ITTIL "Generate ITTI analyzser logs (similar to wireshark logs but with more details)\n"
|
||||
#define CONFIG_HLP_DLMCS "Set the maximum downlink MCS\n"
|
||||
#define CONFIG_HLP_STMON "Enable processing timing measurement of lte softmodem on per subframe basis \n"
|
||||
@@ -81,7 +79,6 @@
|
||||
#define CONFIG_HLP_L2MONW "Enable L2 wireshark messages on localhost \n"
|
||||
#define CONFIG_HLP_L2MONP "Enable L2 pcap messages on localhost \n"
|
||||
#define CONFIG_HLP_VCD "Enable VCD (generated file will is named openair_dump_eNB.vcd, read it with target/RT/USER/eNB.gtkw\n"
|
||||
#define CONFIG_HLP_FLOG "Enable PDCP RCP online log file\n"
|
||||
#define CONFIG_HLP_TQFS "Apply three-quarter of sampling frequency, 23.04 Msps to reduce the data rate on USB/PCIe transfers (only valid for 20 MHz)\n"
|
||||
#define CONFIG_HLP_TPORT "tracer port\n"
|
||||
#define CONFIG_HLP_NOTWAIT "don't wait for tracer, start immediately\n"
|
||||
@@ -168,13 +165,28 @@ extern int16_t dlsch_demod_shift;
|
||||
{"P" , CONFIG_HLP_L2MONP, 0, strptr:(char **)&in_path, defstrval:"/tmp/oai_opt.pcap", TYPE_STRING, sizeof(in_path)}, \
|
||||
{"V" , CONFIG_HLP_VCD, PARAMFLAG_BOOL, iptr:&ouput_vcd, defintval:0, TYPE_INT, 0}, \
|
||||
{"q" , CONFIG_HLP_STMON, PARAMFLAG_BOOL, iptr:&opp_enabled, defintval:0, TYPE_INT, 0}, \
|
||||
{"R" , CONFIG_HLP_FLOG, PARAMFLAG_BOOL, iptr:&online_log_messages, defintval:0, TYPE_INT, 0}, \
|
||||
{"g" , CONFIG_HLP_LOGL, 0, i16ptr:&glog_level, defintval:1, TYPE_INT16, 0}, \
|
||||
{"G" , CONFIG_HLP_LOGV, 0, i16ptr:&glog_verbosity, defintval:0, TYPE_INT16, 0}, \
|
||||
{"S" , CONFIG_HLP_MSLOTS, PARAMFLAG_BOOL, u8ptr:&exit_missed_slots, defintval:1, TYPE_UINT8, 0}, \
|
||||
{"T" , CONFIG_HLP_TDD, PARAMFLAG_BOOL, iptr:&tddflag, defintval:0, TYPE_INT, 0} \
|
||||
}
|
||||
|
||||
#define CONFIG_HLP_FLOG "Enable online log \n"
|
||||
#define CONFIG_HLP_LOGL "Set the global log level, valide options: (9:trace, 8/7:debug, 6:info, 4:warn, 3:error)\n"
|
||||
#define CONFIG_HLP_LOGV "Set the global log verbosity \n"
|
||||
/*---------------------------------------------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
/* command line parameters for LOG utility */
|
||||
/* optname helpstr paramflags XXXptr defXXXval type numelt */
|
||||
/*---------------------------------------------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
#define CMDLINE_LOGPARAMS_DESC { \
|
||||
{"R" , CONFIG_HLP_FLOG, 0, uptr:&online_log_messages, defintval:1, TYPE_INT, 0}, \
|
||||
{"g" , CONFIG_HLP_LOGL, 0, uptr:&glog_level, defintval:0, TYPE_UINT, 0}, \
|
||||
{"G" , CONFIG_HLP_LOGV, 0, uptr:&glog_verbosity, defintval:0, TYPE_UINT16, 0}, \
|
||||
}
|
||||
#define CMDLINE_ONLINELOG_IDX 0
|
||||
#define CMDLINE_GLOGLEVEL_IDX 1
|
||||
#define CMDLINE_GLOGVERBO_IDX 2
|
||||
|
||||
|
||||
|
||||
extern int T_port;
|
||||
extern int T_wait;
|
||||
extern int T_dont_fork;
|
||||
|
||||
Reference in New Issue
Block a user