diff --git a/.codespellrc b/.codespellrc index 087150a6d..9e972389e 100644 --- a/.codespellrc +++ b/.codespellrc @@ -2,4 +2,4 @@ check-filenames = builtin = clear,rare,usage,informal skip = */.git,*/cmake-build-*,*/.idea,*/completions,*/presets,*/screenshots,*/tests,*/3rdparty,*/logo/ascii -ignore-words-list = iterm,compiletime,unknwn,pengwin,siduction,master,sur,doas,conexant +ignore-words-list = iterm,compiletime,unknwn,pengwin,siduction,master,slave,sur,doas,conexant diff --git a/completions/fastfetch.bash b/completions/fastfetch.bash index 76e43859a..abd7fffb7 100644 --- a/completions/fastfetch.bash +++ b/completions/fastfetch.bash @@ -183,6 +183,7 @@ __fastfetch_completion() "--display-precise-refresh-rate" "--localip-show-ipv4" "--localip-show-ipv6" + "--localip-show-flags" "--localip-show-loop" "--localip-name-prefix" "--localip-compact-type" diff --git a/doc/json_schema.json b/doc/json_schema.json index 6a38e48ce..c9bf60831 100644 --- a/doc/json_schema.json +++ b/doc/json_schema.json @@ -1703,6 +1703,11 @@ "type": "boolean", "default": false }, + "showFlags": { + "description": "Show the interface's flags", + "type": "boolean", + "default": false + }, "compact": { "description": "Show all IPs in one line", "type": "boolean", diff --git a/src/data/help.json b/src/data/help.json index 2d99a0b3a..3a326f350 100644 --- a/src/data/help.json +++ b/src/data/help.json @@ -1231,6 +1231,15 @@ "default": false } }, + { + "long": "localip-show-flags", + "desc": "Show net interface flags in local ip module", + "arg": { + "type": "bool", + "optional": true, + "default": false + } + }, { "long": "localip-compact", "desc": "Show all IPs in one line", diff --git a/src/detection/localip/localip.h b/src/detection/localip/localip.h index 859d5340f..7f2304bdf 100644 --- a/src/detection/localip/localip.h +++ b/src/detection/localip/localip.h @@ -8,9 +8,29 @@ typedef struct FFLocalIpResult FFstrbuf ipv4; FFstrbuf ipv6; FFstrbuf mac; + FFstrbuf flags; int32_t mtu; int32_t speed; bool defaultRoute; } FFLocalIpResult; +typedef struct NIFlag +{ + int flag; + const char *name; +} NIFlag; + +static inline void writeNIFlagsToStrBuf(FFstrbuf *buf, int flag, const NIFlag names[]) +{ + for (const NIFlag *nf = names; nf->name != NULL && flag != 0; ++nf) + { + if (flag & nf->flag) { + if (nf - names != 0) + ffStrbufAppendC(buf, ','); + ffStrbufAppendS(buf, nf->name); + flag &= ~nf->flag; + } + } +} + const char* ffDetectLocalIps(const FFLocalIpOptions* options, FFlist* results); diff --git a/src/detection/localip/localip_linux.c b/src/detection/localip/localip_linux.c index 61f64c36b..b41d4eed9 100644 --- a/src/detection/localip/localip_linux.c +++ b/src/detection/localip/localip_linux.c @@ -15,6 +15,7 @@ #ifdef __linux__ #include #include +#include #endif #if defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__APPLE__) @@ -27,6 +28,47 @@ #include #endif +static const NIFlag niFlags[] = { + { IFF_UP, "UP" }, + { IFF_BROADCAST, "BROADCAST" }, + { IFF_DEBUG, "DEBUG" }, + { IFF_LOOPBACK, "LOOPBACK" }, + { IFF_POINTOPOINT, "POINTOPOINT" }, + { IFF_RUNNING, "RUNNING" }, + { IFF_NOARP, "NOARP" }, + { IFF_PROMISC, "PROMISC" }, + { IFF_ALLMULTI, "ALLMULTI" }, + { IFF_MULTICAST, "MULTICAST" }, +#if defined(__linux__) || defined(__APPLE__) || defined(__sun) + { IFF_NOTRAILERS, "NOTRAILERS" }, +#endif +#ifdef __linux__ + { IFF_MASTER, "MASTER" }, + { IFF_SLAVE, "SLAVE" }, + { IFF_PORTSEL, "PORTSEL" }, + { IFF_AUTOMEDIA, "AUTOMEDIA" }, + { IFF_DYNAMIC, "DYNAMIC" }, + { IFF_LOWER_UP, "LOWER_UP" }, + { IFF_DORMANT, "DORMANT" }, + { IFF_ECHO, "ECHO" }, +#endif +#if defined(__FreeBSD__) || defined(__APPLE__) || defined(__OpenBSD__) + { IFF_OACTIVE, "OACTIVE" }, + { IFF_SIMPLEX, "SIMPLEX" }, + { IFF_LINK0, "LINK0" }, + { IFF_LINK1, "LINK1" }, + { IFF_LINK2, "LINK2" }, +#endif +#if defined(__FreeBSD__) || defined(__APPLE__) + { IFF_ALTPHYS, "ALTPHYS" }, +#endif +#ifdef __FreeBSD__ + { IFF_CANTCONFIG, "CANTCONFIG" }, +#endif + // sentinel + { 0, NULL } +}; + static void addNewIp(FFlist* list, const char* name, const char* addr, int type, bool defaultRoute, bool firstOnly) { FFLocalIpResult* ip = NULL; @@ -44,6 +86,7 @@ static void addNewIp(FFlist* list, const char* name, const char* addr, int type, ffStrbufInit(&ip->ipv4); ffStrbufInit(&ip->ipv6); ffStrbufInit(&ip->mac); + ffStrbufInit(&ip->flags); ip->defaultRoute = defaultRoute; ip->mtu = -1; ip->speed = -1; @@ -96,6 +139,7 @@ const char* ffDetectLocalIps(const FFLocalIpOptions* options, FFlist* results) if (options->namePrefix.length && strncmp(ifa->ifa_name, options->namePrefix.chars, options->namePrefix.length) != 0) continue; + bool newIP = false; if (ifa->ifa_addr->sa_family == AF_INET) { if (!(options->showType & FF_LOCALIP_TYPE_IPV4_BIT)) @@ -117,6 +161,7 @@ const char* ffDetectLocalIps(const FFLocalIpOptions* options, FFlist* results) } addNewIp(results, ifa->ifa_name, addressBuffer, AF_INET, isDefaultRoute, !(options->showType & FF_LOCALIP_TYPE_ALL_IPS_BIT)); + newIP = true; } else if (ifa->ifa_addr->sa_family == AF_INET6) { @@ -142,6 +187,7 @@ const char* ffDetectLocalIps(const FFLocalIpOptions* options, FFlist* results) } addNewIp(results, ifa->ifa_name, addressBuffer, AF_INET6, isDefaultRoute, !(options->showType & FF_LOCALIP_TYPE_ALL_IPS_BIT)); + newIP = true; } #if __FreeBSD__ || __OpenBSD__ || __APPLE__ else if (ifa->ifa_addr->sa_family == AF_LINK) @@ -154,6 +200,7 @@ const char* ffDetectLocalIps(const FFLocalIpOptions* options, FFlist* results) snprintf(addressBuffer, sizeof(addressBuffer), "%02x:%02x:%02x:%02x:%02x:%02x", ptr[0], ptr[1], ptr[2], ptr[3], ptr[4], ptr[5]); addNewIp(results, ifa->ifa_name, addressBuffer, -1, isDefaultRoute, false); + newIP = true; } #else else if (ifa->ifa_addr->sa_family == AF_PACKET) @@ -166,8 +213,16 @@ const char* ffDetectLocalIps(const FFLocalIpOptions* options, FFlist* results) snprintf(addressBuffer, sizeof(addressBuffer), "%02x:%02x:%02x:%02x:%02x:%02x", ptr[0], ptr[1], ptr[2], ptr[3], ptr[4], ptr[5]); addNewIp(results, ifa->ifa_name, addressBuffer, -1, isDefaultRoute, false); + newIP = true; } #endif + + if (newIP) + { + FFLocalIpResult* result = FF_LIST_GET(FFLocalIpResult, *results, results->length - 1); + if (options->showType & FF_LOCALIP_TYPE_FLAGS_BIT) + writeNIFlagsToStrBuf(&result->flags, (int)ifa->ifa_flags, niFlags); + } } if (ifAddrStruct) freeifaddrs(ifAddrStruct); diff --git a/src/detection/localip/localip_windows.c b/src/detection/localip/localip_windows.c index f26bb35b8..e6750bac9 100644 --- a/src/detection/localip/localip_windows.c +++ b/src/detection/localip/localip_windows.c @@ -6,6 +6,21 @@ #include "util/windows/unicode.h" #include "localip.h" +static const NIFlag niFlags[] = { + { IP_ADAPTER_DDNS_ENABLED, "DDNS_ENABLED" }, + { IP_ADAPTER_REGISTER_ADAPTER_SUFFIX, "REGISTER_ADAPTER_SUFFIX" }, + { IP_ADAPTER_DHCP_ENABLED, "DHCP_ENABLED" }, + { IP_ADAPTER_RECEIVE_ONLY, "RECEIVE_ONLY" }, + { IP_ADAPTER_NO_MULTICAST, "NO_MULTICAST" }, + { IP_ADAPTER_IPV6_OTHER_STATEFUL_CONFIG, "IPV6_OTHER_STATEFUL_CONFIG" }, + { IP_ADAPTER_NETBIOS_OVER_TCPIP_ENABLED, "NETBIOS_OVER_TCPIP_ENABLED" }, + { IP_ADAPTER_IPV4_ENABLED, "IPV4_ENABLED" }, + { IP_ADAPTER_IPV6_ENABLED, "IPV6_ENABLED" }, + { IP_ADAPTER_IPV6_MANAGE_ADDRESS_CONFIG, "IPV6_MANAGE_ADDRESS_CONFIG" }, + // sentinel + { 0, NULL } +}; + static void addNewIp(FFlist* list, const char* name, const char* addr, int type, bool newIp, bool defaultRoute) { FFLocalIpResult* ip = NULL; @@ -17,6 +32,7 @@ static void addNewIp(FFlist* list, const char* name, const char* addr, int type, ffStrbufInit(&ip->ipv4); ffStrbufInit(&ip->ipv6); ffStrbufInit(&ip->mac); + ffStrbufInit(&ip->flags); ip->defaultRoute = defaultRoute; ip->speed = -1; ip->mtu = -1; @@ -157,6 +173,8 @@ const char* ffDetectLocalIps(const FFLocalIpOptions* options, FFlist* results) result->speed = (int32_t) (adapter->ReceiveLinkSpeed / 1000); if (options->showType & FF_LOCALIP_TYPE_MTU_BIT) result->mtu = (int32_t) adapter->Mtu; + if (options->showType & FF_LOCALIP_TYPE_FLAGS_BIT) + writeNIFlagsToStrBuf(&result->flags, (int)adapter->Flags, niFlags); } } diff --git a/src/modules/localip/localip.c b/src/modules/localip/localip.c index 38e1b67fb..7343f716d 100644 --- a/src/modules/localip/localip.c +++ b/src/modules/localip/localip.c @@ -5,7 +5,7 @@ #include "util/stringUtils.h" #define FF_LOCALIP_DISPLAY_NAME "Local IP" -#define FF_LOCALIP_NUM_FORMAT_ARGS 7 +#define FF_LOCALIP_NUM_FORMAT_ARGS 8 #pragma GCC diagnostic ignored "-Wsign-conversion" static int sortIps(const FFLocalIpResult* left, const FFLocalIpResult* right) @@ -77,6 +77,12 @@ static void printIp(FFLocalIpResult* ip, bool markDefaultRoute) putchar(']'); flag = true; } + if (ip->flags.length) { + if (flag) fputs(" <", stdout); + ffStrbufWriteTo(&ip->flags, stdout); + putchar('>'); + flag = true; + } if (markDefaultRoute && flag && ip->defaultRoute) fputs(" *", stdout); } @@ -151,6 +157,7 @@ void ffPrintLocalIp(FFLocalIpOptions* options) FF_FORMAT_ARG(ip->defaultRoute, "is-default-route"), FF_FORMAT_ARG(ip->mtu, "mtu"), FF_FORMAT_ARG(speedStr, "speed"), + FF_FORMAT_ARG(ip->flags, "flags"), })); } ++index; @@ -163,6 +170,7 @@ void ffPrintLocalIp(FFLocalIpOptions* options) ffStrbufDestroy(&ip->ipv4); ffStrbufDestroy(&ip->ipv6); ffStrbufDestroy(&ip->mac); + ffStrbufDestroy(&ip->flags); } } @@ -236,6 +244,15 @@ bool ffParseLocalIpCommandOptions(FFLocalIpOptions* options, const char* key, co return true; } + if (ffStrEqualsIgnCase(subKey, "show-flags")) + { + if (ffOptionParseBoolean(value)) + options->showType |= FF_LOCALIP_TYPE_FLAGS_BIT; + else + options->showType &= ~FF_LOCALIP_TYPE_FLAGS_BIT; + return true; + } + if(ffStrEqualsIgnCase(subKey, "compact")) { if (ffOptionParseBoolean(value)) @@ -348,6 +365,15 @@ void ffParseLocalIpJsonObject(FFLocalIpOptions* options, yyjson_val* module) continue; } + if (ffStrEqualsIgnCase(key, "showFlags")) + { + if (yyjson_get_bool(val)) + options->showType |= FF_LOCALIP_TYPE_FLAGS_BIT; + else + options->showType &= ~FF_LOCALIP_TYPE_FLAGS_BIT; + continue; + } + if (ffStrEqualsIgnCase(key, "compact")) { if (yyjson_get_bool(val)) @@ -415,6 +441,9 @@ void ffGenerateLocalIpJsonConfig(FFLocalIpOptions* options, yyjson_mut_doc* doc, if (options->showType & FF_LOCALIP_TYPE_SPEED_BIT) yyjson_mut_obj_add_bool(doc, module, "showSpeed", true); + if (options->showType & FF_LOCALIP_TYPE_FLAGS_BIT) + yyjson_mut_obj_add_bool(doc, module, "showFlags", true); + if (options->showType & FF_LOCALIP_TYPE_COMPACT_BIT) yyjson_mut_obj_add_bool(doc, module, "compact", true); @@ -452,6 +481,7 @@ void ffGenerateLocalIpJsonResult(FF_MAYBE_UNUSED FFLocalIpOptions* options, yyjs yyjson_mut_obj_add_strbuf(doc, obj, "name", &ip->name); yyjson_mut_obj_add_int(doc, obj, "mtu", ip->mtu); yyjson_mut_obj_add_int(doc, obj, "speed", ip->speed); + yyjson_mut_obj_add_strbuf(doc, obj, "flags", &ip->flags); } FF_LIST_FOR_EACH(FFLocalIpResult, ip, results) @@ -460,6 +490,7 @@ void ffGenerateLocalIpJsonResult(FF_MAYBE_UNUSED FFLocalIpOptions* options, yyjs ffStrbufDestroy(&ip->ipv4); ffStrbufDestroy(&ip->ipv6); ffStrbufDestroy(&ip->mac); + ffStrbufDestroy(&ip->flags); } } @@ -473,6 +504,7 @@ void ffPrintLocalIpHelpFormat(void) "Is default route - is-default-route", "MTU size in bytes - mtu", "Link speed (formatted) - speed", + "Interface flags - flags", })); } diff --git a/src/modules/localip/option.h b/src/modules/localip/option.h index 1a0161152..511ec729d 100644 --- a/src/modules/localip/option.h +++ b/src/modules/localip/option.h @@ -14,6 +14,7 @@ typedef enum FFLocalIpType FF_LOCALIP_TYPE_PREFIX_LEN_BIT = 1 << 4, FF_LOCALIP_TYPE_MTU_BIT = 1 << 5, FF_LOCALIP_TYPE_SPEED_BIT = 1 << 6, + FF_LOCALIP_TYPE_FLAGS_BIT = 1 << 7, FF_LOCALIP_TYPE_COMPACT_BIT = 1 << 10, FF_LOCALIP_TYPE_DEFAULT_ROUTE_ONLY_BIT = 1 << 11,