diff options
author | Ron Yorston <rmy@pobox.com> | 2015-03-14 20:33:00 +0000 |
---|---|---|
committer | Ron Yorston <rmy@pobox.com> | 2015-03-14 20:33:00 +0000 |
commit | a4f58436b78fe59e57620c6e0301f213ee25f273 (patch) | |
tree | 8355f724926e605280af2d6f2b1ccc6b1bd02dee /networking/wget.c | |
parent | ba0c36cfcf84efbac6f89e27238e04bb57e9cd45 (diff) | |
parent | 49acc1a7618a28d34381cbb7661d7c981fcb238f (diff) | |
download | busybox-w32-a4f58436b78fe59e57620c6e0301f213ee25f273.tar.gz busybox-w32-a4f58436b78fe59e57620c6e0301f213ee25f273.tar.bz2 busybox-w32-a4f58436b78fe59e57620c6e0301f213ee25f273.zip |
Merge branch 'busybox' into merge
Conflicts:
coreutils/od_bloaty.c
libbb/lineedit.c
Diffstat (limited to 'networking/wget.c')
-rw-r--r-- | networking/wget.c | 98 |
1 files changed, 78 insertions, 20 deletions
diff --git a/networking/wget.c b/networking/wget.c index 774accf7a..42bfbb206 100644 --- a/networking/wget.c +++ b/networking/wget.c | |||
@@ -38,8 +38,14 @@ | |||
38 | 38 | ||
39 | #if 0 | 39 | #if 0 |
40 | # define log_io(...) bb_error_msg(__VA_ARGS__) | 40 | # define log_io(...) bb_error_msg(__VA_ARGS__) |
41 | # define SENDFMT(fp, fmt, ...) \ | ||
42 | do { \ | ||
43 | log_io("> " fmt, ##__VA_ARGS__); \ | ||
44 | fprintf(fp, fmt, ##__VA_ARGS__); \ | ||
45 | } while (0); | ||
41 | #else | 46 | #else |
42 | # define log_io(...) ((void)0) | 47 | # define log_io(...) ((void)0) |
48 | # define SENDFMT(fp, fmt, ...) fprintf(fp, fmt, ##__VA_ARGS__) | ||
43 | #endif | 49 | #endif |
44 | 50 | ||
45 | 51 | ||
@@ -55,6 +61,36 @@ static const char P_FTP[] = "ftp"; | |||
55 | static const char P_HTTP[] = "http"; | 61 | static const char P_HTTP[] = "http"; |
56 | static const char P_HTTPS[] = "https"; | 62 | static const char P_HTTPS[] = "https"; |
57 | 63 | ||
64 | #if ENABLE_FEATURE_WGET_LONG_OPTIONS | ||
65 | /* User-specified headers prevent using our corresponding built-in headers. */ | ||
66 | enum { | ||
67 | HDR_HOST = (1<<0), | ||
68 | HDR_USER_AGENT = (1<<1), | ||
69 | HDR_RANGE = (1<<2), | ||
70 | HDR_AUTH = (1<<3) * ENABLE_FEATURE_WGET_AUTHENTICATION, | ||
71 | HDR_PROXY_AUTH = (1<<4) * ENABLE_FEATURE_WGET_AUTHENTICATION, | ||
72 | }; | ||
73 | static const char wget_user_headers[] ALIGN1 = | ||
74 | "Host:\0" | ||
75 | "User-Agent:\0" | ||
76 | "Range:\0" | ||
77 | # if ENABLE_FEATURE_WGET_AUTHENTICATION | ||
78 | "Authorization:\0" | ||
79 | "Proxy-Authorization:\0" | ||
80 | # endif | ||
81 | ; | ||
82 | # define USR_HEADER_HOST (G.user_headers & HDR_HOST) | ||
83 | # define USR_HEADER_USER_AGENT (G.user_headers & HDR_USER_AGENT) | ||
84 | # define USR_HEADER_RANGE (G.user_headers & HDR_RANGE) | ||
85 | # define USR_HEADER_AUTH (G.user_headers & HDR_AUTH) | ||
86 | # define USR_HEADER_PROXY_AUTH (G.user_headers & HDR_PROXY_AUTH) | ||
87 | #else /* No long options, no user-headers :( */ | ||
88 | # define USR_HEADER_HOST 0 | ||
89 | # define USR_HEADER_USER_AGENT 0 | ||
90 | # define USR_HEADER_RANGE 0 | ||
91 | # define USR_HEADER_AUTH 0 | ||
92 | # define USR_HEADER_PROXY_AUTH 0 | ||
93 | #endif | ||
58 | 94 | ||
59 | /* Globals */ | 95 | /* Globals */ |
60 | struct globals { | 96 | struct globals { |
@@ -69,6 +105,7 @@ struct globals { | |||
69 | #if ENABLE_FEATURE_WGET_LONG_OPTIONS | 105 | #if ENABLE_FEATURE_WGET_LONG_OPTIONS |
70 | char *post_data; | 106 | char *post_data; |
71 | char *extra_headers; | 107 | char *extra_headers; |
108 | unsigned char user_headers; /* Headers mentioned by the user */ | ||
72 | #endif | 109 | #endif |
73 | char *fname_out; /* where to direct output (-O) */ | 110 | char *fname_out; /* where to direct output (-O) */ |
74 | const char *proxy_flag; /* Use proxies if env vars are set */ | 111 | const char *proxy_flag; /* Use proxies if env vars are set */ |
@@ -842,43 +879,46 @@ static void download_one_url(const char *url) | |||
842 | #endif | 879 | #endif |
843 | /* Send HTTP request */ | 880 | /* Send HTTP request */ |
844 | if (use_proxy) { | 881 | if (use_proxy) { |
845 | fprintf(sfp, "GET %s://%s/%s HTTP/1.1\r\n", | 882 | SENDFMT(sfp, "GET %s://%s/%s HTTP/1.1\r\n", |
846 | target.protocol, target.host, | 883 | target.protocol, target.host, |
847 | target.path); | 884 | target.path); |
848 | } else { | 885 | } else { |
849 | fprintf(sfp, "%s /%s HTTP/1.1\r\n", | 886 | SENDFMT(sfp, "%s /%s HTTP/1.1\r\n", |
850 | (option_mask32 & WGET_OPT_POST_DATA) ? "POST" : "GET", | 887 | (option_mask32 & WGET_OPT_POST_DATA) ? "POST" : "GET", |
851 | target.path); | 888 | target.path); |
852 | } | 889 | } |
853 | 890 | if (!USR_HEADER_HOST) | |
854 | fprintf(sfp, "Host: %s\r\nUser-Agent: %s\r\n", | 891 | SENDFMT(sfp, "Host: %s\r\n", target.host); |
855 | target.host, G.user_agent); | 892 | if (!USR_HEADER_USER_AGENT) |
893 | SENDFMT(sfp, "User-Agent: %s\r\n", G.user_agent); | ||
856 | 894 | ||
857 | /* Ask server to close the connection as soon as we are done | 895 | /* Ask server to close the connection as soon as we are done |
858 | * (IOW: we do not intend to send more requests) | 896 | * (IOW: we do not intend to send more requests) |
859 | */ | 897 | */ |
860 | fprintf(sfp, "Connection: close\r\n"); | 898 | SENDFMT(sfp, "Connection: close\r\n"); |
861 | 899 | ||
862 | #if ENABLE_FEATURE_WGET_AUTHENTICATION | 900 | #if ENABLE_FEATURE_WGET_AUTHENTICATION |
863 | if (target.user) { | 901 | if (target.user && !USR_HEADER_AUTH) { |
864 | fprintf(sfp, "Proxy-Authorization: Basic %s\r\n"+6, | 902 | SENDFMT(sfp, "Proxy-Authorization: Basic %s\r\n"+6, |
865 | base64enc(target.user)); | 903 | base64enc(target.user)); |
866 | } | 904 | } |
867 | if (use_proxy && server.user) { | 905 | if (use_proxy && server.user && !USR_HEADER_PROXY_AUTH) { |
868 | fprintf(sfp, "Proxy-Authorization: Basic %s\r\n", | 906 | SENDFMT(sfp, "Proxy-Authorization: Basic %s\r\n", |
869 | base64enc(server.user)); | 907 | base64enc(server.user)); |
870 | } | 908 | } |
871 | #endif | 909 | #endif |
872 | 910 | ||
873 | if (G.beg_range != 0) | 911 | if (G.beg_range != 0 && !USR_HEADER_RANGE) |
874 | fprintf(sfp, "Range: bytes=%"OFF_FMT"u-\r\n", G.beg_range); | 912 | SENDFMT(sfp, "Range: bytes=%"OFF_FMT"u-\r\n", G.beg_range); |
875 | 913 | ||
876 | #if ENABLE_FEATURE_WGET_LONG_OPTIONS | 914 | #if ENABLE_FEATURE_WGET_LONG_OPTIONS |
877 | if (G.extra_headers) | 915 | if (G.extra_headers) { |
916 | log_io(G.extra_headers); | ||
878 | fputs(G.extra_headers, sfp); | 917 | fputs(G.extra_headers, sfp); |
918 | } | ||
879 | 919 | ||
880 | if (option_mask32 & WGET_OPT_POST_DATA) { | 920 | if (option_mask32 & WGET_OPT_POST_DATA) { |
881 | fprintf(sfp, | 921 | SENDFMT(sfp, |
882 | "Content-Type: application/x-www-form-urlencoded\r\n" | 922 | "Content-Type: application/x-www-form-urlencoded\r\n" |
883 | "Content-Length: %u\r\n" | 923 | "Content-Length: %u\r\n" |
884 | "\r\n" | 924 | "\r\n" |
@@ -888,7 +928,7 @@ static void download_one_url(const char *url) | |||
888 | } else | 928 | } else |
889 | #endif | 929 | #endif |
890 | { | 930 | { |
891 | fprintf(sfp, "\r\n"); | 931 | SENDFMT(sfp, "\r\n"); |
892 | } | 932 | } |
893 | 933 | ||
894 | fflush(sfp); | 934 | fflush(sfp); |
@@ -1105,7 +1145,9 @@ int wget_main(int argc UNUSED_PARAM, char **argv) | |||
1105 | #if ENABLE_FEATURE_WGET_LONG_OPTIONS | 1145 | #if ENABLE_FEATURE_WGET_LONG_OPTIONS |
1106 | applet_long_options = wget_longopts; | 1146 | applet_long_options = wget_longopts; |
1107 | #endif | 1147 | #endif |
1108 | opt_complementary = "-1" IF_FEATURE_WGET_TIMEOUT(":T+") IF_FEATURE_WGET_LONG_OPTIONS(":\xfe::"); | 1148 | opt_complementary = "-1" |
1149 | IF_FEATURE_WGET_TIMEOUT(":T+") | ||
1150 | IF_FEATURE_WGET_LONG_OPTIONS(":\xfe::"); | ||
1109 | getopt32(argv, "csqO:P:Y:U:T:" /*ignored:*/ "t:", | 1151 | getopt32(argv, "csqO:P:Y:U:T:" /*ignored:*/ "t:", |
1110 | &G.fname_out, &G.dir_prefix, | 1152 | &G.fname_out, &G.dir_prefix, |
1111 | &G.proxy_flag, &G.user_agent, | 1153 | &G.proxy_flag, &G.user_agent, |
@@ -1118,16 +1160,32 @@ int wget_main(int argc UNUSED_PARAM, char **argv) | |||
1118 | 1160 | ||
1119 | #if ENABLE_FEATURE_WGET_LONG_OPTIONS | 1161 | #if ENABLE_FEATURE_WGET_LONG_OPTIONS |
1120 | if (headers_llist) { | 1162 | if (headers_llist) { |
1121 | int size = 1; | 1163 | int size = 0; |
1122 | char *cp; | 1164 | char *hdr; |
1123 | llist_t *ll = headers_llist; | 1165 | llist_t *ll = headers_llist; |
1124 | while (ll) { | 1166 | while (ll) { |
1125 | size += strlen(ll->data) + 2; | 1167 | size += strlen(ll->data) + 2; |
1126 | ll = ll->link; | 1168 | ll = ll->link; |
1127 | } | 1169 | } |
1128 | G.extra_headers = cp = xmalloc(size); | 1170 | G.extra_headers = hdr = xmalloc(size + 1); |
1129 | while (headers_llist) { | 1171 | while (headers_llist) { |
1130 | cp += sprintf(cp, "%s\r\n", (char*)llist_pop(&headers_llist)); | 1172 | int bit; |
1173 | const char *words; | ||
1174 | |||
1175 | size = sprintf(hdr, "%s\r\n", | ||
1176 | (char*)llist_pop(&headers_llist)); | ||
1177 | /* a bit like index_in_substrings but don't match full key */ | ||
1178 | bit = 1; | ||
1179 | words = wget_user_headers; | ||
1180 | while (*words) { | ||
1181 | if (strstr(hdr, words) == hdr) { | ||
1182 | G.user_headers |= bit; | ||
1183 | break; | ||
1184 | } | ||
1185 | bit <<= 1; | ||
1186 | words += strlen(words) + 1; | ||
1187 | } | ||
1188 | hdr += size; | ||
1131 | } | 1189 | } |
1132 | } | 1190 | } |
1133 | #endif | 1191 | #endif |