diff options
Diffstat (limited to 'src/loader')
-rw-r--r-- | src/loader/cgi.nim | 6 | ||||
-rw-r--r-- | src/loader/file.nim | 6 | ||||
-rw-r--r-- | src/loader/loader.nim | 24 |
3 files changed, 29 insertions, 7 deletions
diff --git a/src/loader/cgi.nim b/src/loader/cgi.nim index d94a2243..b0341a59 100644 --- a/src/loader/cgi.nim +++ b/src/loader/cgi.nim @@ -54,7 +54,11 @@ proc loadCGI*(handle: LoaderHandle, request: Request, cgiDir: seq[string]) = if cgiDir.len == 0: discard handle.sendResult(ERROR_NO_CGI_DIR) return - let path = percentDecode(request.url.pathname) + var path = percentDecode(request.url.pathname) + if path.startsWith("/cgi-bin/"): + path.delete(0 .. "/cgi-bin/".high) + elif path.startsWith("/$LIB/"): + path.delete(0 .. "/$LIB/".high) if path == "" or request.url.hostname != "": discard handle.sendResult(ERROR_INVALID_CGI_PATH) return diff --git a/src/loader/file.nim b/src/loader/file.nim index 5d552e40..cdb7afc2 100644 --- a/src/loader/file.nim +++ b/src/loader/file.nim @@ -108,11 +108,7 @@ proc loadFile(handle: LoaderHandle, istream: Stream) = if n < bufferSize: break -proc loadFilePath*(handle: LoaderHandle, url: URL) = - when defined(windows) or defined(OS2) or defined(DOS): - let path = url.path.serialize_unicode_dos() - else: - let path = url.path.serialize_unicode() +proc loadFilePath*(handle: LoaderHandle, url: URL, path: string) = let istream = newFileStream(path, fmRead) if istream == nil: if dirExists(path): diff --git a/src/loader/loader.nim b/src/loader/loader.nim index a148b77b..1f313a64 100644 --- a/src/loader/loader.nim +++ b/src/loader/loader.nim @@ -103,6 +103,7 @@ type acceptProxy*: bool cgiDir*: seq[string] uriMethodMap*: URIMethodMap + w3mCGICompat*: bool FetchPromise* = Promise[JSResult[Response]] @@ -114,6 +115,16 @@ proc addFd(ctx: LoaderContext, fd: int, flags: int) = const MaxRewrites = 2 # should be enough? TODO find out what w3m thinks +func canRewriteForCGICompat(ctx: LoaderContext, path: string): bool = + if not ctx.config.w3mCGICompat: + return false + if path.startsWith("/cgi-bin/") or path.startsWith("/$LIB/"): + return true + for dir in ctx.config.cgiDir: + if path.startsWith(dir): + return true + return false + proc loadResource(ctx: LoaderContext, request: Request, handle: LoaderHandle) = var redo = true var tries = 0 @@ -121,7 +132,15 @@ proc loadResource(ctx: LoaderContext, request: Request, handle: LoaderHandle) = redo = false case request.url.scheme of "file": - handle.loadFilePath(request.url) + let path = request.url.path.serialize_unicode() + if ctx.canRewriteForCGICompat(path): + let newURL = newURL("cgi-bin:" & path & request.url.search) + if newURL.isSome: + request.url = newURL.get + inc tries + redo = true + continue + handle.loadFilePath(request.url, path) handle.close() of "http", "https": let handleData = handle.loadHttp(ctx.curlm, request) @@ -280,6 +299,9 @@ proc initLoaderContext(fd: cint, config: LoaderConfig): LoaderContext = discard sig gctx.exitLoader() ctx.addFd(int(ctx.ssock.sock.getFd()), CURL_WAIT_POLLIN) + for dir in ctx.config.cgiDir.mitems: + if dir.len > 0 and dir[^1] != '/': + dir &= '/' return ctx proc runFileLoader*(fd: cint, config: LoaderConfig) = |