source: tools/langserver/src/main.cpp @ b52abe0

ADTarm-ehast-experimentalenumforall-pointer-decayjacob/cs343-translationnew-astnew-ast-unique-exprpthread-emulationqualifiedEnum
Last change on this file since b52abe0 was b52abe0, checked in by Thierry Delisle <tdelisle@…>, 4 years ago

Implemented basic language server with no capabilities

  • Property mode set to 100644
File size: 2.2 KB
Line 
1#include <iostream>
2#include <string>
3#include <vector>
4
5#include "json.hpp"
6#include "log.hpp"
7
8static void request(std::vector<char> & buf);
9
10namespace server {
11        json::obj init(const json::obj & ) {
12                return {
13                        { "capabilities", json::obj::array() },
14                        { "serverInfo", {
15                                { "name", "Cforall Language Server" },
16                                { "version", "0.1" }
17                        }}
18                };
19        }
20}
21
22std::unordered_map<std::string, json::obj (*)( const json::obj & )> actions {
23        { "initialize", server::init }
24};
25
26int main(int argc, char * argv[]) {
27        g_argc = argc;
28        g_argv = argv;
29
30        log() << "Language Server called with args:" << std::endl;
31        for(int i = 0; i < argc; i++) {
32                log() << "\t- " << argv[i] << std::endl;
33        }
34
35        std::vector<char> buffer;
36        while(true) {
37                request(buffer);
38                if(buffer.size() == 0) break;
39
40                auto top = json::parse(buffer);
41
42                auto action = actions.find( top["method"] );
43                if(action != actions.end()) {
44                        log() << "Executing request '" << action->first << "'" << std::endl;
45                        json::obj response = {
46                                {"id", top["id"] }
47                        };
48
49                        try{
50                                response["result"] = action->second( top["params"] );
51                        } catch( const json::obj & error ) {
52                                response["result"] = "";
53                                response["error"] = error;
54                        }
55                        log() << "Responding with : " << response.dump(4) << std::endl;
56                        std::cout << response.dump() << std::endl;
57                }
58                else {
59                        log() << "WARNING no action for method '" << top["method"].dump(4) << "'" << std::endl;
60                }
61        }
62
63        log() << "Language Server closing after end of file" << std::endl;
64
65        return 0;
66}
67
68static void request(std::vector<char> & buffer) {
69        std::string lenstr;
70        std::getline( std::cin, lenstr );
71        if(std::cin.eof()) { buffer.clear(); return; };
72
73        if (lenstr.rfind("Content-Length: ", 0) != 0) {
74                log() << "Expected content length bug got '" << lenstr << "' instead " << std::endl;
75                std::exit(EXIT_FAILURE);
76        }
77
78        size_t idx = sizeof("Content-Length:");
79        size_t end;
80        size_t len = std::stoul(lenstr.substr(idx), &end);
81        if(lenstr.length() != (idx + end + 1)) {
82                log() << "Inconsistent size of integer in content length: " << lenstr.length() << " vs " << (idx + end) << std::endl;
83        }
84
85        log() << "New request of " << len << " bytes" << std::endl;
86        buffer.resize( len + 2 );
87        std::cin.read(buffer.data(), buffer.size());
88        return;
89}
Note: See TracBrowser for help on using the repository browser.