Skip to content

Commit

Permalink
plugin: add plugin framework.
Browse files Browse the repository at this point in the history
  • Loading branch information
pymumu committed Jan 21, 2024
1 parent acf49e4 commit 903c7d5
Show file tree
Hide file tree
Showing 18 changed files with 851 additions and 17 deletions.
5 changes: 5 additions & 0 deletions etc/smartdns/smartdns.conf
Original file line number Diff line number Diff line change
Expand Up @@ -395,3 +395,8 @@ log-level info
# group-begin [group-name]
# group-match [-g|group group-name] [-domain domain] [-client-ip [ip-cidr|mac|ip-set]]
# group-end

# load plugin
# plugin [path/to/file] [args]
# plugin /usr/lib/smartdns/libsmartdns-ui.so --p 8080 -i 0.0.0.0 -r /usr/share/smartdns/wwwroot

4 changes: 4 additions & 0 deletions plugin/demo/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
.vscode
*.o
*.so
*.swp.
45 changes: 45 additions & 0 deletions plugin/demo/Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@

# Copyright (C) 2018-2024 Ruilin Peng (Nick) <[email protected]>.
#
# smartdns is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# smartdns is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.

BIN=smartdns-demo.so
OBJS_MAIN=$(patsubst %.c,%.o,$(wildcard *.c))
OBJS=$(OBJS_MAIN)

# cflags
ifndef CFLAGS
ifdef DEBUG
CFLAGS = -g -DDEBUG
else
CFLAGS = -O2
endif
CFLAGS +=-fPIC -Wall -Wstrict-prototypes -fno-omit-frame-pointer -Wstrict-aliasing -funwind-tables -Wmissing-prototypes -Wshadow -Wextra -Wno-unused-parameter -Wno-implicit-fallthrough
endif

override CFLAGS +=-Iinclude -I../../src/include -I../../src
override CFLAGS += -DBASE_FILE_NAME='"$(notdir $<)"'
override CFLAGS += $(EXTRA_CFLAGS)

override LDFLAGS += -lpthread -shared

.PHONY: all clean

all: $(BIN)

$(BIN) : $(OBJS)
$(CC) $(OBJS) -o $@ $(LDFLAGS)

clean:
$(RM) $(OBJS) $(BIN)
49 changes: 49 additions & 0 deletions plugin/demo/demo.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
#include "demo.h"
#include "dns_server.h"
#include "util.h"
#include <arpa/inet.h>
#include <netinet/in.h>
#include <stdio.h>
#include <sys/socket.h>
#include <tlog.h>

static int demo_server_recv(struct dns_packet *packet, unsigned char *inpacket, int inpacket_len,
struct sockaddr_storage *local, socklen_t local_len, struct sockaddr_storage *from,
socklen_t from_len)
{
char hostname[256] = {0};
tlog(TLOG_INFO, "recv packet from %s", get_host_by_addr(hostname, sizeof(hostname), (struct sockaddr *)from));
return 0;
}

static void demo_server_request_complete(struct dns_request *request)
{
tlog(TLOG_INFO, "server complete request, request domain is %s", dns_server_request_get_domain(request));
}

struct smartdns_operations demo_ops = {
.server_recv = demo_server_recv,
.server_query_complete = demo_server_request_complete,
};

int dns_plugin_init(struct dns_plugin *plugin)
{
char options[4096] = {0};
int argc = dns_plugin_get_argc(plugin);
const char **argv = dns_plugin_get_argv(plugin);

for (int i = 0; i < argc; i++) {
snprintf(options + strlen(options), sizeof(options) - strlen(options), "%s ", argv[i]);
}

tlog(TLOG_INFO, "demo plugin init, options: %s", options);
smartdns_operations_register(&demo_ops);
return 0;
}

int dns_plugin_exit(struct dns_plugin *plugin)
{
tlog(TLOG_INFO, "demo plugin exit.");
smartdns_operations_unregister(&demo_ops);
return 0;
}
15 changes: 15 additions & 0 deletions plugin/demo/demo.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@

#ifndef SMART_DNS_PLUGIN_DEMO_H
#define SMART_DNS_PLUGIN_DEMO_H

#include "dns_plugin.h"

#ifdef __cplusplus
extern "C" {
#endif /*__cplusplus */


#ifdef __cplusplus
}
#endif /*__cplusplus */
#endif
8 changes: 3 additions & 5 deletions src/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -48,13 +48,11 @@ endif
CXXFLAGS=-O2 -g -Wall -std=c++11
override CXXFLAGS +=-Iinclude

# ldflags
ifeq ($(STATIC), yes)
override LDFLAGS += -lssl -lcrypto -Wl,--whole-archive -lpthread -Wl,--no-whole-archive -ldl -lm -static
else ifeq ($(SSL_STATIC), yes)
override LDFLAGS += -Wl,-Bstatic -lssl -lcrypto -Wl,-Bdynamic -lpthread -ldl -lm
override CFLAGS += -DBUILD_STATIC
override LDFLAGS += -lssl -lcrypto -Wl,--whole-archive -lpthread -Wl,--no-whole-archive -ldl -lm -static -rdynamic
else
override LDFLAGS += -lssl -lcrypto -lpthread -ldl -lm
override LDFLAGS += -lssl -lcrypto -lpthread -ldl -lm -rdynamic
endif

.PHONY: all clean
Expand Down
23 changes: 14 additions & 9 deletions src/dns_cache.c
Original file line number Diff line number Diff line change
Expand Up @@ -496,6 +496,19 @@ void dns_cache_data_get(struct dns_cache_data *cache_data)
return;
}

void dns_cache_flush(void)
{
struct dns_cache *dns_cache = NULL;
struct dns_cache *tmp = NULL;

pthread_mutex_lock(&dns_cache_head.lock);
list_for_each_entry_safe(dns_cache, tmp, &dns_cache_head.cache_list, list)
{
_dns_cache_remove(dns_cache);
}
pthread_mutex_unlock(&dns_cache_head.lock);
}

void dns_cache_data_put(struct dns_cache_data *cache_data)
{
if (cache_data == NULL) {
Expand Down Expand Up @@ -853,19 +866,11 @@ int dns_cache_print(const char *file)

void dns_cache_destroy(void)
{
struct dns_cache *dns_cache = NULL;
struct dns_cache *tmp = NULL;

if (is_cache_init == 0) {
return;
}

pthread_mutex_lock(&dns_cache_head.lock);
list_for_each_entry_safe(dns_cache, tmp, &dns_cache_head.cache_list, list)
{
_dns_cache_remove(dns_cache);
}
pthread_mutex_unlock(&dns_cache_head.lock);
dns_cache_flush();

pthread_mutex_destroy(&dns_cache_head.lock);
hash_table_free(dns_cache_head.cache_hash, free);
Expand Down
2 changes: 2 additions & 0 deletions src/dns_cache.h
Original file line number Diff line number Diff line change
Expand Up @@ -166,6 +166,8 @@ void dns_cache_data_get(struct dns_cache_data *cache_data);

void dns_cache_data_put(struct dns_cache_data *cache_data);

void dns_cache_flush(void);

void dns_cache_destroy(void);

int dns_cache_load(const char *file);
Expand Down
93 changes: 93 additions & 0 deletions src/dns_conf.c
Original file line number Diff line number Diff line change
Expand Up @@ -169,6 +169,8 @@ struct conf_file_path {
char file[DNS_MAX_PATH];
};

struct dns_conf_plugin_table dns_conf_plugin_table;

char dns_conf_sni_proxy_ip[DNS_MAX_IPLEN];

static int _conf_domain_rule_nameserver(const char *domain, const char *group_name);
Expand Down Expand Up @@ -5451,6 +5453,81 @@ static int _config_client_rules(void *data, int argc, char *argv[])
return -1;
}

static struct dns_conf_plugin *_config_get_plugin(const char *file)
{
uint32_t key = 0;
struct dns_conf_plugin *plugin = NULL;

key = hash_string(file);
hash_for_each_possible(dns_conf_plugin_table.plugins, plugin, node, key)
{
if (strncmp(plugin->file, file, DNS_MAX_PATH) != 0) {
continue;
}

return plugin;
}

return NULL;
}

static int _config_plugin(void *data, int argc, char *argv[])
{
#ifdef BUILD_STATIC
tlog(TLOG_ERROR, "plugin not support in static release, please install dynamic release.");
goto errout;
#endif
char file[DNS_MAX_PATH];
unsigned int key = 0;
int i = 0;
char *ptr = NULL;
char *ptr_end = NULL;

if (argc < 1) {
tlog(TLOG_ERROR, "invalid parameter.");
goto errout;
}

conf_get_conf_fullpath(argv[1], file, sizeof(file));
if (file[0] == '\0') {
tlog(TLOG_ERROR, "plugin: invalid parameter.");
goto errout;
}

struct dns_conf_plugin *plugin = _config_get_plugin(file);
if (plugin != NULL) {
tlog(TLOG_ERROR, "plugin '%s' already exists.", file);
goto errout;
}

if (access(file, F_OK) != 0) {
tlog(TLOG_ERROR, "plugin '%s' not exists.", file);
goto errout;
}

plugin = malloc(sizeof(*plugin));
if (plugin == NULL) {
goto errout;
}
memset(plugin, 0, sizeof(*plugin));
safe_strncpy(plugin->file, file, sizeof(plugin->file) - 1);
ptr = plugin->args;
ptr_end = plugin->args + sizeof(plugin->args) - 2;
for (i = 1; i < argc && ptr < ptr_end; i++) {
safe_strncpy(ptr, argv[i], ptr_end - ptr - 1);
ptr += strlen(argv[i]) + 1;
}
plugin->argc = argc - 1;
plugin->args_len = ptr - plugin->args;

key = hash_string(file);
hash_add(dns_conf_plugin_table.plugins, &plugin->node, key);

return 0;
errout:
return -1;
}

int dns_server_check_update_hosts(void)
{
struct stat statbuf;
Expand Down Expand Up @@ -5672,6 +5749,7 @@ static struct config_item _config_item[] = {
CONF_YESNO("debug-save-fail-packet", &dns_save_fail_packet),
CONF_YESNO("no-pidfile", &dns_no_pidfile),
CONF_YESNO("no-daemon", &dns_no_daemon),
CONF_CUSTOM("plugin", _config_plugin, NULL),
CONF_STRING("resolv-file", (char *)&dns_resolv_file, sizeof(dns_resolv_file)),
CONF_STRING("debug-save-fail-packet-dir", (char *)&dns_save_fail_packet_dir, sizeof(dns_save_fail_packet_dir)),
CONF_CUSTOM("conf-file", config_additional_file, NULL),
Expand Down Expand Up @@ -5854,6 +5932,7 @@ static int _dns_server_load_conf_init(void)
hash_init(dns_domain_set_name_table.names);
hash_init(dns_ip_set_name_table.names);
hash_init(dns_conf_srv_record_table.srv);
hash_init(dns_conf_plugin_table.plugins);

_config_current_group_push_default();

Expand Down Expand Up @@ -5909,6 +5988,19 @@ static void _config_client_rule_destroy(void)
_config_client_rule_destroy_mac();
}

static void _config_plugin_table_destroy(void)
{
struct dns_conf_plugin *plugin = NULL;
struct hlist_node *tmp = NULL;
unsigned long i = 0;

hash_for_each_safe(dns_conf_plugin_table.plugins, i, tmp, plugin, node)
{
hlist_del_init(&plugin->node);
free(plugin);
}
}

void dns_server_load_exit(void)
{
_config_rule_group_destroy();
Expand All @@ -5920,6 +6012,7 @@ void dns_server_load_exit(void)
_config_host_table_destroy(0);
_config_proxy_table_destroy();
_config_srv_record_table_destroy();
_config_plugin_table_destroy();

dns_conf_server_num = 0;
dns_server_bind_destroy();
Expand Down
13 changes: 13 additions & 0 deletions src/dns_conf.h
Original file line number Diff line number Diff line change
Expand Up @@ -615,6 +615,19 @@ extern struct dns_dns64 dns_conf_dns_dns64;
extern struct dns_bind_ip dns_conf_bind_ip[DNS_MAX_BIND_IP];
extern int dns_conf_bind_ip_num;

struct dns_conf_plugin {
struct hlist_node node;
char name[DNS_MAX_CNAME_LEN];
char file[DNS_MAX_PATH];
char args[DNS_MAX_PATH * 4];
int argc;
int args_len;
};
struct dns_conf_plugin_table {
DECLARE_HASHTABLE(plugins, 4);
};
extern struct dns_conf_plugin_table dns_conf_plugin_table;

extern char dns_conf_bind_ca_file[DNS_MAX_PATH];
extern char dns_conf_bind_ca_key_file[DNS_MAX_PATH];
extern char dns_conf_bind_ca_key_pass[DNS_MAX_PATH];
Expand Down
Loading

0 comments on commit 903c7d5

Please sign in to comment.