コード例 #1
0
ファイル: commands.c プロジェクト: ProfDrLuigi/zanka
static void wd_cmd_ban(wi_array_t *arguments) {
	wd_client_t		*client = wd_client();
	wd_client_t		*peer;
	wd_uid_t		uid;
	
	if(!client->account->ban_users) {
		wd_reply(516, WI_STR("Permission Denied"));
		
		return;
	}

	uid = wi_string_uint32(WI_ARRAY(arguments, 0));
	peer = wd_client_with_uid(uid);

	if(!peer) {
		wd_reply(512, WI_STR("Client Not Found"));

		return;
	}

	if(peer->account->cannot_be_kicked) {
		wd_reply(515, WI_STR("Cannot Be Disconnected"));

		return;
	}

	wd_broadcast_lock();
	wd_broadcast(WD_PUBLIC_CID, 307, WI_STR("%u%c%u%c%#@"),
				 peer->uid,		WD_FIELD_SEPARATOR,
				 client->uid,	WD_FIELD_SEPARATOR,
				 WI_ARRAY(arguments, 1));
	wd_broadcast_unlock();

	wi_log_ll(WI_STR("%@/%@/%@ banned %@/%@/%@"),
		client->nick, client->login, client->ip,
		peer->nick, peer->login, peer->ip);

	wd_tempban(peer->ip);

	wi_lock_lock(peer->flag_lock);
	peer->state = WD_CLIENT_STATE_DISCONNECTED;
	wi_lock_unlock(peer->flag_lock);
}
コード例 #2
0
ファイル: commands.c プロジェクト: ProfDrLuigi/zanka
static void wd_cmd_decline(wi_array_t *arguments) {
	wd_client_t		*client = wd_client();
	wd_chat_t		*chat;
	wd_cid_t		cid;
	
	cid = wi_string_uint32(WI_ARRAY(arguments, 0));
	chat = wd_chat_with_cid(cid);
	
	if(!chat)
		return;

	if(wd_chat_contains_client(chat, client))
		return;

	wd_broadcast_lock();
	wd_broadcast(chat->cid, 332, WI_STR("%u%c%u"),
				 chat->cid,		WD_FIELD_SEPARATOR,
				 client->uid);
	wd_broadcast_unlock();
}
コード例 #3
0
ファイル: commands.c プロジェクト: ProfDrLuigi/zanka
static void wd_cmd_msg(wi_array_t *arguments) {
	wd_client_t		*client = wd_client();
	wd_client_t		*peer;
	wd_uid_t		uid;

	uid = wi_string_uint32(WI_ARRAY(arguments, 0));
	peer = wd_client_with_uid(uid);

	if(!peer) {
		wd_reply(512, WI_STR("Client Not Found"));

		return;
	}

	wd_client_lock_socket(peer);
	wd_sreply(peer->socket, 305, WI_STR("%u%c%#@"),
			  client->uid,	WD_FIELD_SEPARATOR,
			  WI_ARRAY(arguments, 1));
	wd_client_unlock_socket(peer);
}
コード例 #4
0
ファイル: wi-p7-message.c プロジェクト: ProfDrLuigi/zanka
wi_boolean_t wi_p7_message_get_uint32_for_name(wi_p7_message_t *p7_message, wi_p7_uint32_t *value, wi_string_t *field_name) {
	wi_string_t		*string;
	wi_p7_int32_t	p7_int32;
	
	if(p7_message->serialization == WI_P7_BINARY) {
		if(!wi_p7_message_get_int32_for_name(p7_message, &p7_int32, field_name))
			return false;
		
		*value = (wi_p7_uint32_t) p7_int32;
	} else {
		string = _wi_p7_message_xml_value_for_name(p7_message, field_name);
		
		if(!string)
			return false;
		
		*value = wi_string_uint32(string);
	}
	
	return true;
}
コード例 #5
0
ファイル: client.c プロジェクト: ProfDrLuigi/zanka
static void wr_msg_200(wi_array_t *arguments) {
	wi_string_t		*password;
	double			protocol;
	
	protocol = wi_string_double(wr_protocol_version_string);
	
	wr_server = wr_server_init(wr_server_alloc());
	wr_server->version = wi_retain(WI_ARRAY(arguments, 0));
	wr_server->protocol = wi_string_double(WI_ARRAY(arguments, 1));
	wr_server->name = wi_retain(WI_ARRAY(arguments, 2));
	wr_server->description = wi_retain(WI_ARRAY(arguments, 3));
	wr_server->startdate = wi_date_init_with_rfc3339_string(wi_date_alloc(), WI_ARRAY(arguments, 4));
	wr_server->files = wi_string_uint32(WI_ARRAY(arguments, 5));
	wr_server->size = wi_string_uint64(WI_ARRAY(arguments, 6));

	wr_draw_divider();
	
	if(!wr_logged_in) {
		if(wr_server->protocol > protocol) {
			wr_wprintf_prefix(wr_console_window, WI_STR("Server protocol version %.1f may not be fully compatible with client protocol version %.1f"),
				wr_server->protocol, protocol);
		}

		wr_send_command(WI_STR("CLIENT %#@"), wr_client_version_string);
		wr_send_command(WI_STR("NICK %#@"), wr_nick);
		wr_send_command(WI_STR("STATUS %#@"), wr_status);
		wr_send_command(WI_STR("ICON %u%c%#@"), 0, WR_FIELD_SEPARATOR, wr_icon);
		wr_send_command(WI_STR("USER %#@"), wr_login ? wr_login : WI_STR("guest"));
		
		if(wr_password && wi_string_length(wr_password) > 0)
			password = wi_string_sha1(wr_password);
		else
			password = NULL;

		wr_send_command(WI_STR("PASS %#@"), password);
		
		wr_send_command(WI_STR("WHO %u"), 1);

		wr_logged_in = true;
	}
}
コード例 #6
0
ファイル: commands.c プロジェクト: ProfDrLuigi/zanka
static void wd_cmd_leave(wi_array_t *arguments) {
	wd_client_t		*client = wd_client();
	wd_chat_t		*chat;
	wd_cid_t		cid;

	cid = wi_string_uint32(WI_ARRAY(arguments, 0));

	if(cid == WD_PUBLIC_CID)
		return;

	chat = wd_chat_with_cid(cid);

	if(!chat)
		return;

	wd_chat_remove_client(chat, client);

	wd_broadcast_lock();
	wd_client_broadcast_leave(client, cid);
	wd_broadcast_unlock();
}
コード例 #7
0
ファイル: client.c プロジェクト: ProfDrLuigi/zanka
static void wr_msg_305(wi_array_t *arguments) {
	wr_user_t		*user;
	wr_window_t		*window;
	wr_uid_t		uid;

	uid = wi_string_uint32(WI_ARRAY(arguments, 0));
	user = wr_chat_user_with_uid(wr_public_chat, uid);

	if(user && !wr_is_ignored(wr_user_nick(user))) {
		window = wr_windows_window_with_user(user);
		
		if(!window) {
			window = wr_window_init_with_user(wr_window_alloc(), user);
			wr_windows_add_window(window);
			wi_release(window);
		}
		
		wr_wprint_msg(window, wr_user_nick(user), WI_ARRAY(arguments, 1));
		wr_reply_uid = wr_user_id(user);
	}
}
コード例 #8
0
ファイル: wi-settings.c プロジェクト: ProfDrLuigi/zanka
wi_boolean_t _wi_settings_set_user(wi_settings_t *settings, wi_uinteger_t index, wi_string_t *name, wi_string_t *value) {
	struct passwd		*user;
	uint32_t			uid;
	
	user = getpwnam(wi_string_cstring(value));
	
	if(!user) {
		uid = wi_string_uint32(value);
		
		if(uid != 0 || wi_is_equal(value, WI_STR("0")))
			user = getpwuid(uid);
	}
	
	if(!user) {
		wi_error_set_libwired_error(WI_ERROR_SETTINGS_NOSUCHUSER);
		
		return false;
	}

	*(uid_t *) settings->spec[index].setting = user->pw_uid;
	
	return true;
}
コード例 #9
0
ファイル: client.c プロジェクト: ProfDrLuigi/zanka
static void wr_msg_304(wi_array_t *arguments) {
	wi_string_t		*nick;
	wr_user_t		*user;
	wr_uid_t		uid;

	uid = wi_string_uint32(WI_ARRAY(arguments, 0));
	user = wr_chat_user_with_uid(wr_public_chat, uid);

	if(user) {
		nick = WI_ARRAY(arguments, 4);
		
		if(!wi_is_equal(wr_user_nick(user), nick)) {
			wr_wprintf_prefix(wr_console_window, WI_STR("%@ is now known as %@"),
				wr_user_nick(user), nick);

			wr_user_set_nick(user, nick);
		}

		wr_user_set_idle(user, wi_string_bool(WI_ARRAY(arguments, 1)));
		wr_user_set_admin(user, wi_string_bool(WI_ARRAY(arguments, 2)));
		wr_user_set_status(user, WI_ARRAY(arguments, 5));
	}
}
コード例 #10
0
ファイル: commands.c プロジェクト: ProfDrLuigi/wirebot
static void wr_command_unignore(wi_array_t *arguments) {
	wi_enumerator_t	*enumerator;
	wi_string_t		*string;
	wr_ignore_t		*ignore;
	wr_iid_t		iid;

	if(wi_array_count(arguments) > 0) {
		string = WI_ARRAY(arguments, 0);
		iid = wi_string_uint32(string);
		
		if(iid > 0)
			ignore = wr_ignore_with_iid(iid);
		else
			ignore = wr_ignore_with_string(string);
		
		if(ignore) {
			wr_printf_prefix(WI_STR("No longer ignoring \"%@\""),
				wr_ignore_string(ignore));
			
			wi_mutable_array_remove_data(wr_ignores, ignore);
		} else {
			wr_printf_prefix(WI_STR("No ignore matching \"%@\""), string);
		}
	} else {
		wr_printf_prefix(WI_STR("Ignores:"));

		if(wi_array_count(wr_ignores) == 0) {
			wr_printf_block(WI_STR("(none)"));
		} else {
			enumerator = wi_array_data_enumerator(wr_ignores);
			
			while((ignore = wi_enumerator_next_data(enumerator)))
				wr_printf_block(WI_STR("%u: %@"), wr_ignore_id(ignore), wr_ignore_string(ignore));
		}
	}
}
コード例 #11
0
ファイル: commands.c プロジェクト: ProfDrLuigi/zanka
static void wd_cmd_info(wi_array_t *arguments) {
	wd_client_t			*client = wd_client();
	wi_list_node_t		*node;
	wi_string_t			*info, *login, *idle, *downloads, *uploads;
	wd_client_t			*peer;
	wd_transfer_t		*transfer;
	wd_uid_t			uid;

	if(!client->account->get_user_info) {
		wd_reply(516, WI_STR("Permission Denied"));
		
		return;
	}

	uid = wi_string_uint32(WI_ARRAY(arguments, 0));
	peer = wd_client_with_uid(uid);

	if(!peer) {
		wd_reply(512, WI_STR("Client Not Found"));

		return;
	}
	
	downloads	= wi_string();
	uploads		= wi_string();

	wi_list_rdlock(wd_transfers);
	WI_LIST_FOREACH(wd_transfers, node, transfer) {
		if(transfer->client == peer && transfer->state == WD_TRANSFER_RUNNING) {
			if(!client->account->view_dropboxes) {
				if(wd_files_path_is_dropbox(transfer->path))
					continue;
			}
			
			info = wi_string_with_format(WI_STR("%#@%c%llu%c%llu%c%u"),
										 transfer->path,		WD_RECORD_SEPARATOR,
										 transfer->transferred,	WD_RECORD_SEPARATOR,
										 transfer->size,		WD_RECORD_SEPARATOR,
										 transfer->speed);
			
			if(transfer->type == WD_TRANSFER_DOWNLOAD) {
				if(wi_string_length(downloads) > 0)
					wi_string_append_format(downloads, WI_STR("%c"), WD_GROUP_SEPARATOR);

				wi_string_append_string(downloads, info);
			} else {
				if(wi_string_length(uploads) > 0)
					wi_string_append_format(uploads, WI_STR("%c"), WD_GROUP_SEPARATOR);

				wi_string_append_string(uploads, info);
			}
		}
	}
	wi_list_unlock(wd_transfers);
	
	login	= wi_date_iso8601_string(wi_date_with_time_interval(peer->login_time));
	idle	= wi_date_iso8601_string(wi_date_with_time_interval(peer->idle_time));

	wd_reply(308, WI_STR("%u%c%u%c%u%c%u%c%#@%c%#@%c%#@%c%#@%c%#@%c%#@%c%u%c%#@%c%#@%c%#@%c%#@%c%#@%c%#@"),
			 peer->uid,								WD_FIELD_SEPARATOR,
			 peer->idle,							WD_FIELD_SEPARATOR,
			 peer->admin,							WD_FIELD_SEPARATOR,
			 peer->icon,							WD_FIELD_SEPARATOR,
			 peer->nick,							WD_FIELD_SEPARATOR,
			 peer->login,							WD_FIELD_SEPARATOR,
			 peer->ip,								WD_FIELD_SEPARATOR,
			 peer->host,							WD_FIELD_SEPARATOR,
			 peer->version,							WD_FIELD_SEPARATOR,
			 wi_socket_cipher_name(peer->socket),	WD_FIELD_SEPARATOR,
			 wi_socket_cipher_bits(peer->socket),	WD_FIELD_SEPARATOR,
			 login,									WD_FIELD_SEPARATOR,
			 idle,									WD_FIELD_SEPARATOR,
			 downloads,								WD_FIELD_SEPARATOR,
			 uploads,								WD_FIELD_SEPARATOR,
			 peer->status,							WD_FIELD_SEPARATOR,
			 peer->image);
}
コード例 #12
0
ファイル: wi-settings.c プロジェクト: ProfDrLuigi/zanka
wi_boolean_t _wi_settings_set_number(wi_settings_t *settings, uint32_t index, wi_string_t *name, wi_string_t *value) {
	*(uint32_t *) settings->spec[index].setting = wi_string_uint32(value);
	
	return true;
}
コード例 #13
0
ファイル: client.c プロジェクト: ProfDrLuigi/zanka
static void wr_msg_308(wi_array_t *arguments) {
	wi_enumerator_t		*enumerator;
	wi_date_t			*date;
	wi_array_t			*array, *transfers;
	wi_string_t			*string, *interval, *name, *transferred, *size, *speed;
	wi_uinteger_t		n;
	wi_boolean_t		first;
	
	wr_printf_prefix(WI_STR("User info:"),
		WI_ARRAY(arguments, 4));

	wr_printf_block(WI_STR("Nick:        %@"), WI_ARRAY(arguments, 4));

	if(wr_server->protocol >= 1.1)
		wr_printf_block(WI_STR("Status:      %@"), WI_ARRAY(arguments, 15));

	wr_printf_block(WI_STR("Login:       %@"), WI_ARRAY(arguments, 5));
	wr_printf_block(WI_STR("ID:          %@"), WI_ARRAY(arguments, 0));
	wr_printf_block(WI_STR("Address:     %@"), WI_ARRAY(arguments, 6));
	wr_printf_block(WI_STR("Host:        %@"), WI_ARRAY(arguments, 7));
	wr_printf_block(WI_STR("Client:      %@"), WI_ARRAY(arguments, 8));
	wr_printf_block(WI_STR("Cipher:      %@/%@ bits"), WI_ARRAY(arguments, 9), WI_ARRAY(arguments, 10));

	date = wi_date_with_rfc3339_string(WI_ARRAY(arguments, 11));
	interval = wi_time_interval_string(wi_date_time_interval_since_now(date));
    string = wi_date_string_with_format(date, WI_STR("%a %b %e %T %Y"));
	wr_printf_block(WI_STR("Login Time:  %@, since %@"), interval, string);

	date = wi_date_with_rfc3339_string(WI_ARRAY(arguments, 12));
	interval = wi_time_interval_string(wi_date_time_interval_since_now(date));
    string = wi_date_string_with_format(date, WI_STR("%a %b %e %T %Y"));
	wr_printf_block(WI_STR("Idle Time:   %@, since %@"), interval, string);
	
	for(n = WR_TRANSFER_DOWNLOAD; n <= WR_TRANSFER_UPLOAD; n++) {
		string		= WI_ARRAY(arguments, (n == WR_TRANSFER_DOWNLOAD) ? 13 : 14);
		transfers	= wi_string_components_separated_by_string(string, WI_STR(WR_GROUP_SEPARATOR_STR));
		enumerator	= wi_array_data_enumerator(transfers);
		first		= true;
		
		while((string = wi_enumerator_next_data(enumerator))) {
			array	= wi_string_components_separated_by_string(string, WI_STR(WR_RECORD_SEPARATOR_STR));
			
			if(wi_array_count(array) == 4) {
				name		= wi_string_last_path_component(WI_ARRAY(array, 0));
				transferred	= wr_files_string_for_size(wi_string_uint64(WI_ARRAY(array, 1)));
				size		= wr_files_string_for_size(wi_string_uint64(WI_ARRAY(array, 2)));
				speed		= wr_files_string_for_size(wi_string_uint32(WI_ARRAY(array, 3)));
				
				if(first) {
					if(n == WR_TRANSFER_DOWNLOAD) {
						wr_printf_block(WI_STR("Downloads:   %@, %@ of %@, %@/s"),
							name, transferred, size, speed);
					} else {
						wr_printf_block(WI_STR("Uploads:     %@, %@ of %@, %@/s"),
							name, transferred, size, speed);
					}
				} else {
					wr_printf_block(WI_STR("             %@, %@ of %@, %@/s"),
						name, transferred, size, speed);
				}
			}
			
			first = false;
		}
	}
}
コード例 #14
0
ファイル: client.c プロジェクト: ProfDrLuigi/zanka
static void wr_msg_402(wi_array_t *arguments) {
	wi_date_t			*date;
	wi_string_t			*path, *kind, *string;
	wr_file_t			*file;
	wr_transfer_t		*transfer;
	wi_file_offset_t	size;
	wr_file_type_t		type;

	path = WI_ARRAY(arguments, 0);
	type = wi_string_uint32(WI_ARRAY(arguments, 1));
	size = wi_string_uint64(WI_ARRAY(arguments, 2));

	if(wr_stat_state == WR_STAT_FILE) {
		wr_printf_prefix(WI_STR("File info for %@:"), wi_string_last_path_component(path));
		
		wr_printf_block(WI_STR("Path:      %@"), path);

		switch(type) {
			case WR_FILE_FILE:
				kind = WI_STR("File");
				break;

			case WR_FILE_DIRECTORY:
				kind = WI_STR("Folder");
				break;

			case WR_FILE_UPLOADS:
				kind = WI_STR("Uploads Folder");
				break;

			case WR_FILE_DROPBOX:
				kind = WI_STR("Drop Box Folder");
				break;
			
			default:
				kind = NULL;
				break;
		}

		wr_printf_block(WI_STR("Kind:      %@"), kind);
		
		if(type == WR_FILE_FILE)
			string = wr_files_string_for_size(size);
		else
			string = wr_files_string_for_count(size);
		
		wr_printf_block(WI_STR("Size:      %@"), string);

		date = wi_date_with_rfc3339_string(WI_ARRAY(arguments, 3));
		string = wi_date_string_with_format(date, WI_STR("%a %b %e %T %Y"));
		wr_printf_block(WI_STR("Created:   %@"), string);

		date = wi_date_with_rfc3339_string(WI_ARRAY(arguments, 4));
		string = wi_date_string_with_format(date, WI_STR("%a %b %e %T %Y"));
		wr_printf_block(WI_STR("Modified:  %@"), string);

		if(type == WR_FILE_FILE)
			wr_printf_block(WI_STR("Checksum:  %@"), WI_ARRAY(arguments, 5));

		if(wr_server->protocol >= 1.1)
			wr_printf_block(WI_STR("Comment:   %@"), WI_ARRAY(arguments, 6));
	}
	else if(wr_stat_state == WR_STAT_TRANSFER) {
		transfer = wr_transfers_transfer_with_remote_path(WI_ARRAY(arguments, 0));
		
		if(transfer) {
			if(type == WR_FILE_FILE) {
				if(transfer->checksum && !wi_is_equal(transfer->checksum, WI_ARRAY(arguments, 5))) {
					wr_printf_prefix(WI_STR("get: Checksum mismatch for \"%@\""),
						transfer->name);
					
					wr_transfer_stop(transfer);
					
					return;
				}
				
				if(!transfer->recursive) {
					file = wr_file_init_with_arguments(wr_file_alloc(), arguments);
					wr_transfer_download_add_file(transfer, file, false);
					wi_release(file);
				}
				
				wr_transfer_request(transfer);
			} else {
				wr_ls_state = WR_LS_TRANSFER;
				transfer->recursive = true;
				
				wr_files_clear();
				wr_send_command(WI_STR("LISTRECURSIVE %#@"), path);
			}
		}
	}
}
コード例 #15
0
ファイル: commands.c プロジェクト: ProfDrLuigi/zanka
static void wt_cmd_register(wi_array_t *arguments) {
	wt_client_t					*client = wt_client();
	wi_enumerator_t				*enumerator;
	wi_array_t					*array;
	wi_address_t				*address, *hostaddress;
	wi_url_t					*url;
	wi_string_t					*hostname;
	wt_server_t					*server;
	wi_boolean_t				failed = false, passed;
	uint32_t					bandwidth;

	url			= wi_autorelease(wi_url_init_with_string(wi_url_alloc(), WI_ARRAY(arguments, 1)));
	hostname	= wi_url_host(url);
	address		= wi_socket_address(client->socket);
	
	if(!wi_url_is_valid(url)) {
		/* invalid URL */
		if(wt_settings.strictlookup) {
			wt_reply(503, WI_STR("Syntax Error"));
			wi_log_warn(WI_STR("Register from %@ as \"%@\" URL %@ aborted: %s"),
				client->ip, WI_ARRAY(arguments, 2), WI_ARRAY(arguments, 1),
				"Invalid URL");
			
			return;
		}
		
		failed = true;
		goto failed;
	}

	if(wi_ip_version(hostname) > 0) {
		/* hostname is numeric, compare with source address */
		if(!wi_is_equal(hostname, client->ip)) {
			/* IP mismatch */
			if(wt_settings.strictlookup) {
				wt_reply(530, WI_STR("Address Mismatch"));
				wi_log_warn(WI_STR("Register from %@ as \"%@\" URL %@ denied: %s"),
					client->ip, WI_ARRAY(arguments, 2), WI_ARRAY(arguments, 1),
					"IP mismatch");

				return;
			}

			failed = true;
			goto failed;
		}
	} else {
		/* hostname is symbolic */
		if(wt_settings.lookup) {
			/* look up and compare with source address */
			passed = false;
			array = wi_host_addresses(wi_host_with_string(hostname));
			
			if(array) {
				enumerator = wi_array_data_enumerator(array);
				
				while((hostaddress = wi_enumerator_next_data(enumerator))) {
					if(wi_is_equal(hostaddress, address)) {
						passed = true;
						
						break;
					}
				}
			}
			
			if(!passed) {
				/* lookup failed */
				if(wt_settings.strictlookup) {
					wt_reply(531, WI_STR("Address Mismatch"));
					wi_log_warn(WI_STR("Register from %@ as \"%@\" URL %@ denied: %s"),
						client->ip, WI_ARRAY(arguments, 2), WI_ARRAY(arguments, 1),
						"Lookup failed");
					
					return;
				}
				
				failed = true;
				goto failed;
			}
		}

		if(wt_settings.reverselookup) {
			/* reverse look up and compare to hostname */
			if(!wi_is_equal(wi_address_hostname(address), hostname)) {
				/* reverse lookup failed */
				if(wt_settings.strictlookup) {
					wt_reply(531, WI_STR("Address Mismatch"));
					wi_log_warn(WI_STR("Register from %@ as \"%@\" URL % denied: %@"),
						client->ip, WI_ARRAY(arguments, 2), WI_ARRAY(arguments, 1),
						"Reverse lookup failed");

					return;
				}

				failed = true;
				goto failed;
			}
		}
	}

failed:
	/* get bandwidth */
	bandwidth = wi_string_uint32(WI_ARRAY(arguments, 3));

	/* bandwidth too low? */
	if(wt_settings.minbandwidth > 0 && bandwidth < wt_settings.minbandwidth) {
		wt_reply(516, WI_STR("Permission Denied"));
		wi_log_warn(WI_STR("Register from %@ as \"%@\" URL %@ denied: Bandwidth %.0f Kbps considered too low"),
			client->ip, WI_ARRAY(arguments, 2), WI_ARRAY(arguments, 1), bandwidth / 128.0);

		return;
	}

	/* bandwidth too high? */
	if(wt_settings.maxbandwidth > 0 && bandwidth > wt_settings.maxbandwidth) {
		wt_reply(516, WI_STR("Permission Denied"));
		wi_log_warn(WI_STR("Register from %@ as \"%@\" URL %@ denied: Bandwidth %.0f Kbps considered too high"),
			client->ip, WI_ARRAY(arguments, 2), WI_ARRAY(arguments, 1), bandwidth / 128.0);

		return;
	}

	/* is there an existing server from this host? */
	server = wt_servers_server_with_ip(client->ip);

	if(server) {
		if(server->port == wi_url_port(url)) {
			/* remove existing server in preparation for re-registration */
			wt_servers_remove_stats_for_server(server);
			wt_servers_remove_server(server);
		} else {
			/* multiple servers from the same IP allowed? */
			if(!wt_settings.allowmultiple) {
				wt_reply(530, WI_STR("Address Registered"));
				wi_log_warn(WI_STR("Register from %@ as \"%@\" URL %@ denied: %s"),
					client->ip, WI_ARRAY(arguments, 2), WI_ARRAY(arguments, 1),
					"A server from the same address is already registered");
				
				return;
			}
		}
	}
	
	/* rewrite URL if host verification failed */
	if(failed) {
		wi_url_set_scheme(url, WI_STR("wired"));
		wi_url_set_host(url, client->ip);

		if(wi_string_length(WI_ARRAY(arguments, 1)) == 0)
			wi_log_info(WI_STR("Rewriting URL to %@"), wi_url_string(url));
		else
			wi_log_info(WI_STR("Rewriting URL from %@ to %@"), WI_ARRAY(arguments, 1), wi_url_string(url));
	}

	/* create new server */
	server					= wt_server_init(wt_server_alloc());
	server->key				= wi_retain(wi_string_sha1(wi_autorelease(wi_string_init_random_string_with_length(wi_string_alloc(), 1024))));
	server->port			= wi_url_port(url);
	server->bandwidth		= bandwidth;
	server->register_time	= wi_time_interval();
	server->update_time		= 0.0;
	server->ip				= wi_retain(client->ip);
	server->category		= wt_servers_category_is_valid(WI_ARRAY(arguments, 0))
		? wi_retain(WI_ARRAY(arguments, 0))
		: wi_string_init(wi_string_alloc());
	server->name			= wi_retain(WI_ARRAY(arguments, 2));
	server->description		= wi_retain(WI_ARRAY(arguments, 4));
	server->url				= wi_copy(wi_url_string(url));

	wt_servers_add_server(server);
	wt_servers_add_stats_for_server(server);
	
	/* reply 700 */
	wt_reply(700, WI_STR("%@"), server->key);
	wi_log_info(WI_STR("Registered \"%@\" with URL %@"), server->name, server->url);
	wt_servers_write_file();
	wi_release(server);
}
コード例 #16
0
ファイル: client.c プロジェクト: ProfDrLuigi/zanka
static void wr_msg_402(wi_array_t *arguments) {
	wi_date_t			*date;
	wi_string_t			*path, *kind, *string;
	wr_transfer_t		*transfer;
	wi_file_offset_t	size;
	wr_file_type_t		type;

	path = WI_ARRAY(arguments, 0);
	type = wi_string_uint32(WI_ARRAY(arguments, 1));
	size = wi_string_uint64(WI_ARRAY(arguments, 2));

	if(wr_stat_state == WR_STAT_FILE) {
		wr_printf_prefix(WI_STR("File info for %@:"), wi_string_last_path_component(path));
		
		wr_printf_block(WI_STR("Path:      %@"), path);

		switch(type) {
			case WR_FILE_FILE:
				kind = WI_STR("File");
				break;

			case WR_FILE_DIRECTORY:
				kind = WI_STR("Folder");
				break;

			case WR_FILE_UPLOADS:
				kind = WI_STR("Uploads Folder");
				break;

			case WR_FILE_DROPBOX:
				kind = WI_STR("Drop Box Folder");
				break;
			
			default:
				kind = NULL;
				break;
		}

		wr_printf_block(WI_STR("Kind:      %@"), kind);
		
		if(type == WR_FILE_FILE)
			string = wr_files_string_for_size(size);
		else
			string = wr_files_string_for_count(size);
		
		wr_printf_block(WI_STR("Size:      %@"), string);

		date = wi_date_with_iso8601_string(WI_ARRAY(arguments, 3));
		string = wi_date_string_with_format(date, WI_STR("%a %b %e %T %Y"));
		wr_printf_block(WI_STR("Created:   %@"), string);

		date = wi_date_with_iso8601_string(WI_ARRAY(arguments, 4));
		string = wi_date_string_with_format(date, WI_STR("%a %b %e %T %Y"));
		wr_printf_block(WI_STR("Modified:  %@"), string);

		if(type == WR_FILE_FILE)
			wr_printf_block(WI_STR("Checksum:  %@"), WI_ARRAY(arguments, 5));

		if(wr_server->protocol >= 1.1)
			wr_printf_block(WI_STR("Comment:   %@"), WI_ARRAY(arguments, 6));
	}
	else if(wr_stat_state == WR_STAT_TRANSFER) {
		transfer = wr_transfers_transfer_with_path(WI_ARRAY(arguments, 0));
		
		if(transfer) {
			if(type != WR_FILE_FILE) {
				wr_printf_prefix(WI_STR("get: Cannot download directories"));
				wr_transfer_stop(transfer);
				
				return;
			}
			
			if(transfer->checksum && !wi_is_equal(transfer->checksum, WI_ARRAY(arguments, 5))) {
				wr_printf_prefix(WI_STR("get: Checksum mismatch for \"%@\""),
					transfer->name);
				wr_transfer_stop(transfer);
				
				return;
			}

			transfer->size = size;
			
			wr_send_command(WI_STR("GET %#@%c%llu"),
				transfer->path,		WR_FIELD_SEPARATOR,
				transfer->offset);
		}
	}
}
コード例 #17
0
ファイル: wi-config.c プロジェクト: asvitkine/phxd
static wi_runtime_instance_t * _wi_config_instance_for_setting(wi_config_t *config, wi_string_t *name, wi_string_t *value, wi_config_type_t *type) {
	struct passwd		*user;
	struct group		*group;
	struct servent		*servent;
	wi_uinteger_t		port;
	uint32_t			uid, gid;
	
	if(!wi_dictionary_contains_key(config->types, name)) {
		wi_error_set_libwired_error(WI_ERROR_SETTINGS_UNKNOWNSETTING);
		
		return NULL;
	}
	
	*type = wi_number_int32(wi_dictionary_data_for_key(config->types, name));
	
	switch(*type) {
		case WI_CONFIG_INTEGER:
			return wi_number_with_integer(wi_string_integer(value));
			break;
			
		case WI_CONFIG_BOOL:
			return wi_number_with_bool(wi_string_bool(value));
			break;
			
		case WI_CONFIG_STRING:
		case WI_CONFIG_STRINGLIST:
		case WI_CONFIG_PATH:
			return value;
			break;
			
		case WI_CONFIG_USER:
			user = getpwnam(wi_string_cstring(value));
			
			if(!user) {
				uid = wi_string_uint32(value);
				
				if(uid != 0 || wi_is_equal(value, WI_STR("0")))
					user = getpwuid(uid);
			}
			
			if(!user) {
				wi_error_set_libwired_error(WI_ERROR_SETTINGS_NOSUCHUSER);
				
				return NULL;
			}
			
			return wi_number_with_int32(user->pw_uid);
			break;
			
		case WI_CONFIG_GROUP:
			group = getgrnam(wi_string_cstring(value));
			
			if(!group) {
				gid = wi_string_uint32(value);
				
				if(gid != 0 || wi_is_equal(value, WI_STR("0")))
					group = getgrgid(gid);
			}
			
			if(!group) {
				wi_error_set_libwired_error(WI_ERROR_SETTINGS_NOSUCHGROUP);
				
				return NULL;
			}
			
			return wi_number_with_int32(group->gr_gid);
			break;
			
		case WI_CONFIG_PORT:
			port = wi_string_uinteger(value);
			
			if(port > 65535) {
				wi_error_set_libwired_error(WI_ERROR_SETTINGS_INVALIDPORT);
				
				return NULL;
			}
			
			if(port == 0) {
				servent = getservbyname(wi_string_cstring(value), "tcp");
				
				if(!servent) {
					wi_error_set_libwired_error(WI_ERROR_SETTINGS_NOSUCHSERVICE);
					
					return NULL;
				}
				
				port = servent->s_port;
			}
			
			return wi_number_with_int32(port);
			break;
			
		case WI_CONFIG_REGEXP:
			return wi_autorelease(wi_regexp_init_with_string(wi_regexp_alloc(), value));
			break;
			
		case WI_CONFIG_TIME_INTERVAL:
			return wi_number_with_double(wi_string_double(value));
			break;
	}
	
	return NULL;
}
コード例 #18
0
ファイル: main.c プロジェクト: ProfDrLuigi/zanka
int main(int argc, const char **argv) {
	wi_mutable_array_t		*arguments;
	wi_pool_t				*pool;
	wi_string_t				*string, *root_path;
	int						ch, facility;
	wi_boolean_t			test_config, daemonize, change_directory, switch_user;

	/* init libwired */
	wi_initialize();
	wi_load(argc, argv);
	
	pool					= wi_pool_init(wi_pool_alloc());
	wi_log_syslog			= true;
	wi_log_syslog_facility	= LOG_DAEMON;

	/* init core systems */
	wt_version_init();
	wt_status_lock			= wi_lock_init(wi_lock_alloc());
	wt_start_date			= wi_date_init(wi_date_alloc());
	
	/* set defaults */
	root_path				= WI_STR(WT_ROOT);
	wi_settings_config_path	= wi_string_init_with_cstring(wi_string_alloc(), WT_CONFIG_PATH);
	test_config				= false;
	daemonize				= true;
	change_directory		= true;
	switch_user				= true;

	/* init reexec argument list */
	arguments				= wi_array_init(wi_mutable_array_alloc());

	/* parse command line switches */
	while((ch = getopt(argc, (char * const *) argv, "46Dd:f:hi:L:ls:tuVvXx")) != -1) {
		switch(ch) {
			case '4':
				wt_address_family = WI_ADDRESS_IPV4;
				break;

			case '6':
				wt_address_family = WI_ADDRESS_IPV6;
				break;

			case 'D':
				daemonize = false;
				wi_log_stderr = true;
				break;

			case 'd':
				root_path = wi_string_with_cstring(optarg);
				break;

			case 'f':
				wi_release(wi_settings_config_path);
				wi_settings_config_path = wi_string_init_with_cstring(wi_string_alloc(), optarg);
				break;

			case 'i':
				wi_log_limit = wi_string_uint32(wi_string_with_cstring(optarg));
				break;

			case 'L':
				wi_log_syslog = false;
				wi_log_file = true;

				wi_release(wi_log_path);
				wi_log_path = wi_string_init_with_cstring(wi_string_alloc(), optarg);
				break;

			case 'l':
				wi_log_level++;
				break;

			case 's':
				string = wi_string_with_cstring(optarg);
				facility = wi_log_syslog_facility_with_name(string);
				
				if(facility < 0)
					wi_log_fatal(WI_STR("Could not find syslog facility \"%@\": %m"), string);
				
				wi_log_syslog_facility = facility;
				break;

			case 't':
				test_config = true;
				break;

			case 'u':
				break;

			case 'V':
			case 'v':
				wt_version();
				break;
				
			case 'X':
				daemonize = false;
				break;
				
			case 'x':
				daemonize = false;
				change_directory = false;
				switch_user = false;
				break;
			
			case '?':
			case 'h':
			default:
				wt_usage();
				break;
		}
		
		wi_mutable_array_add_data(arguments, wi_string_with_format(WI_STR("-%c"), ch));
		
		if(optarg)
			wi_mutable_array_add_data(arguments, wi_string_with_cstring(optarg));
	}
	
	/* detach */
	if(daemonize) {
		wi_mutable_array_add_data(arguments, WI_STR("-X"));
		
		switch(wi_fork()) {
			case -1:
				wi_log_fatal(WI_STR("Could not fork: %m"));
				break;
				
			case 0:
				if(!wi_execv(wi_string_with_cstring(argv[0]), arguments))
					wi_log_fatal(WI_STR("Could not execute %s: %m"), argv[0]);
				break;
				
				default:
				_exit(0);
				break;
		}
	}
	
	wi_release(arguments);
	
	/* change directory */
	if(change_directory) {
		if(!wi_fs_change_directory(root_path))
			wi_log_error(WI_STR("Could not change directory to %@: %m"), root_path);
	}
	
	/* open log */
	wi_log_open();

	/* init subsystems */
	wt_ssl_init();
	wt_clients_init();
	wt_servers_init();

	/* read the config file */
	wt_settings_init();

	if(!wt_settings_read_config())
		exit(1);

	/* apply settings */
	wt_settings_apply_settings();

	if(test_config) {
		printf("Config OK\n");

		exit(0);
	}

	/* dump command line */
	wi_log_info(WI_STR("Started as %@ %@"),
		wi_process_path(wi_process()),
		wi_array_components_joined_by_string(wi_process_arguments(wi_process()), WI_STR(" ")));

	/* init tracker */
	wi_log_info(WI_STR("Starting Wired Tracker version %@"), wt_version_string);
	wt_tracker_init();

	/* switch user/group */
	if(switch_user)
		wi_switch_user(wt_settings.user, wt_settings.group);
		
	/* create tracker threads after privilege drop */
	wt_signals_init();
	wt_block_signals();
	wt_servers_schedule();
	wt_tracker_create_threads();
	wt_write_pid();
	wt_write_status(true);
	
	/* clean up pool after startup */
	wi_pool_drain(pool);
	
	/* enter the signal handling thread in the main thread */
	wt_signal_thread(NULL);

	/* dropped out */
	wt_cleanup();
	wi_log_close();
	wi_release(pool);

	return 0;
}
コード例 #19
0
ファイル: wi-p7-message.c プロジェクト: ProfDrLuigi/zanka
void wi_p7_message_deserialize(wi_p7_message_t *p7_message, wi_p7_serialization_t serialization) {
	xmlDocPtr					doc;
	xmlNodePtr					root_node, field_node;
	wi_string_t					*field_name, *field_value;
	wi_p7_spec_message_t		*message;
	wi_p7_spec_field_t			*field;
	wi_uuid_t					*uuid;
	wi_date_t					*date;
	wi_data_t					*data;
	
	if(serialization == WI_P7_BINARY) {
		p7_message->binary_id = wi_read_swap_big_to_host_int32(p7_message->binary_buffer, 0);
		
		message = wi_p7_spec_message_with_id(p7_message->spec, p7_message->binary_id);
		
		if(message)
			p7_message->name = wi_retain(wi_p7_spec_message_name(message));
	} else {
		p7_message->binary_capacity	= _WI_P7_MESSAGE_BINARY_BUFFER_INITIAL_SIZE;
		p7_message->binary_buffer	= wi_malloc(p7_message->binary_capacity);
		p7_message->binary_size		= WI_P7_MESSAGE_BINARY_HEADER_SIZE;
		
		doc							= xmlParseDoc((xmlChar *) wi_string_cstring(p7_message->xml_string));
		root_node					= xmlDocGetRootElement(doc);
		
		if(root_node) {
			wi_p7_message_set_name(p7_message, wi_xml_node_attribute_with_name(root_node, WI_STR("name")));
			
			for(field_node = root_node->children; field_node != NULL; field_node = field_node->next) {
				if(field_node->type == XML_ELEMENT_NODE) {
					if(wi_is_equal(wi_xml_node_name(field_node), WI_STR("field"))) {
						field_name		= wi_xml_node_attribute_with_name(field_node, WI_STR("name"));
						field_value		= wi_xml_node_content(field_node);
						field			= wi_p7_spec_field_with_name(p7_message->spec, field_name);
						
						if(!field_name || !field_value || !field)
							continue;
						
						switch(wi_p7_spec_type_id(wi_p7_spec_field_type(field))) {
							case WI_P7_BOOL:
								wi_p7_message_set_bool_for_name(p7_message, wi_string_bool(field_value), field_name);
								break;
								
							case WI_P7_ENUM:
								wi_p7_message_set_enum_for_name(p7_message, wi_string_uint32(field_value), field_name);
								break;
								
							case WI_P7_INT32:
								wi_p7_message_set_int32_for_name(p7_message, wi_string_int32(field_value), field_name);
								break;
								
							case WI_P7_UINT32:
								wi_p7_message_set_uint32_for_name(p7_message, wi_string_uint32(field_value), field_name);
								break;
								
							case WI_P7_INT64:
								wi_p7_message_set_int64_for_name(p7_message, wi_string_int64(field_value), field_name);
								break;
								
							case WI_P7_UINT64:
								wi_p7_message_set_uint64_for_name(p7_message, wi_string_uint64(field_value), field_name);
								break;
								
							case WI_P7_DOUBLE:
								wi_p7_message_set_double_for_name(p7_message, wi_string_double(field_value), field_name);
								break;
								
							case WI_P7_STRING:
								wi_p7_message_set_string_for_name(p7_message, field_value, field_name);
								break;
								
							case WI_P7_UUID:
								uuid = wi_uuid_with_string(field_value);

								if(uuid)
									wi_p7_message_set_uuid_for_name(p7_message, uuid, field_name);
								break;
								
							case WI_P7_DATE:
								date = wi_date_with_rfc3339_string(field_value);
								
								if(date)
									wi_p7_message_set_date_for_name(p7_message, date, field_name);
								break;
								
							case WI_P7_DATA:
								data = wi_autorelease(wi_data_init_with_base64(wi_data_alloc(), field_value));
								
								if(data)
									wi_p7_message_set_data_for_name(p7_message, data, field_name);
								break;
							
							case WI_P7_OOBDATA:
								wi_p7_message_set_oobdata_for_name(p7_message, wi_string_uint64(field_value), field_name);
								break;
							
							case WI_P7_LIST:
								WI_ASSERT(0, "Can't deserialize XML with lists at the moment");
								break;
						}
					}
				}
			}
		}
		
		xmlFreeDoc(doc);
	}
}
コード例 #20
0
ファイル: main.c プロジェクト: ProfDrLuigi/zanka
int main(int argc, const char **argv) {
	wi_pool_t			*pool;
	wi_string_t			*string;
	int					ch, facility;
	wi_boolean_t		no_chroot, test_config;

	/* init libwired */
	wi_initialize();
	wi_load(argc, argv);
	
	pool					= wi_pool_init(wi_pool_alloc());
	wi_log_startup			= true;
	wi_log_syslog			= true;
	wi_log_syslog_facility	= LOG_DAEMON;

	/* init core systems */
	wt_init_version();
	wt_status_lock			= wi_lock_init(wi_lock_alloc());
	wt_start_date			= wi_date_init(wi_date_alloc());
	
	/* set defaults */
	wi_root_path			= wi_string_init_with_cstring(wi_string_alloc(), WT_ROOT);
	wi_settings_config_path	= wi_string_init_with_cstring(wi_string_alloc(), WT_CONFIG_PATH);
	no_chroot				= false;
	test_config				= false;

	/* parse command line switches */
	while((ch = getopt(argc, (char * const *) argv, "46Dd:f:hi:L:ls:tuVv")) != -1) {
		switch(ch) {
			case '4':
				wt_address_family = WI_ADDRESS_IPV4;
				break;

			case '6':
				wt_address_family = WI_ADDRESS_IPV6;
				break;

			case 'D':
				wt_daemonize = false;
				wi_log_stderr = true;
				break;

			case 'd':
				wi_release(wi_root_path);
				wi_root_path = wi_string_init_with_cstring(wi_string_alloc(), optarg);
				break;

			case 'f':
				wi_release(wi_settings_config_path);
				wi_settings_config_path = wi_string_init_with_cstring(wi_string_alloc(), optarg);
				break;

			case 'i':
				wi_log_limit = wi_string_uint32(wi_string_with_cstring(optarg));
				break;

			case 'L':
				wi_log_syslog = false;
				wi_log_file = true;

				wi_release(wi_log_path);
				wi_log_path = wi_string_init_with_cstring(wi_string_alloc(), optarg);
				break;

			case 'l':
				wi_log_level++;
				break;

			case 's':
				string = wi_string_with_cstring(optarg);
				facility = wi_log_syslog_facility_with_name(string);
				
				if(facility < 0) {
					wi_log_err(WI_STR("Could not find syslog facility \"%@\": %m"),
						string);
				}
				
				wi_log_syslog_facility = facility;
				break;

			case 't':
				test_config = true;
				break;

			case 'u':
				no_chroot = true;
				break;

			case 'V':
			case 'v':
				wt_version();
				break;

			case '?':
			case 'h':
			default:
				wt_usage();
				break;
		}
	}
	
	/* open log */
	wi_log_open();

	/* init subsystems */
	wt_init_ssl();
	wt_init_clients();
	wt_init_servers();

	/* read the config file */
	wt_settings_chroot = !no_chroot;
	wt_init_settings();

	if(!wt_read_config())
		exit(1);

	/* change root directory */
	if(!no_chroot) {
		if(!wi_change_root())
			wi_log_err(WI_STR("Could not change root to %@: %m"), wi_root_path);
	}

	/* apply config */
	wt_apply_config();

	if(test_config) {
		printf("Config OK\n");

		exit(0);
	}

	/* dump command line */
	if(wi_log_level >= WI_LOG_DEBUG) {
		wi_log_debug(WI_STR("Started as %@ %@"),
			wi_process_path(wi_process()),
			wi_array_components_joined_by_string(wi_process_arguments(wi_process()), WI_STR(" ")));
	}

	/* init tracker */
	wi_log_info(WI_STR("Starting Wired Tracker version %@"), wt_version_string);
	wt_init_tracker();

	/* detach (don't chdir, don't close i/o channels) */
	if(wt_daemonize) {
		if(!wi_daemon())
			wi_log_err(WI_STR("Could not become a daemon: %m"));
	}

	/* switch user/group */
	wi_switch_user(wt_settings.user, wt_settings.group);
		
	/* create tracker threads after privilege drop */
	wt_init_signals();
	wt_block_signals();
	wt_schedule_servers();
	wt_fork_tracker();
	wt_write_pid();
	wt_write_status(true);
	wi_log_startup = false;
	
	wi_release(pool);
	pool = wi_pool_init(wi_pool_alloc());
	
	/* enter the signal handling thread in the main thread */
	wt_signal_thread(NULL);

	/* dropped out */
	wt_cleanup();
	wi_log_close();
	wi_release(pool);

	return 0;
}