// File: /workspace/github_cpp_makefile_star2_O3/LiGaCu[P]Distributed_System_to_Compute_the_Shortest_Path/client.cpp
// Function: main
int main(int argc, char *argv[])
{
    int TCPfd;
    struct addrinfo hints, *servinfo, *p;

    int rv;

    char buf[MAXDATASIZE];int numbytes;
    char mapid; int srcVtxid,dstVtxid,filesize;
    float Tt,Tp;
    int path[11]; float mindistan;

    if (argc != 5) 
    {
        fprintf(stderr,"usage: [map id]  [src Vertex] [dst Vertex] [filesize]\n");
        exit(1);
    }

    memset(&hints, 0, sizeof hints);
    hints.ai_family = AF_UNSPEC;
    hints.ai_socktype = SOCK_STREAM;

    if ((rv = getaddrinfo("127.0.0.1", AWS_PORT, &hints, &servinfo)) != 0) 
    {
        fprintf(stderr, "getaddrinfo: %s\n", gai_strerror(rv));
        return 1;
    }

    //The following socket connection codes are from Beej's tutorial
    // loop through all the results and connect to the first we can
    for(p = servinfo; p != NULL; p = p->ai_next) 
    {
        if ((TCPfd = socket(p->ai_family, p->ai_socktype, p->ai_protocol)) == -1) 
        {
            perror("client: socket");
            continue;
        }

        if (connect(TCPfd, p->ai_addr, p->ai_addrlen) == -1) 
        {
            close(TCPfd);
            perror("client: connect");
            continue;
        }
        break;
    }
    if (p == NULL) 
    {
        fprintf(stderr, "client: failed to connect\n");
        return 2;
    }
    freeaddrinfo(servinfo); // all done with this structure

    std::cout << "The client is up and running" << "\n" << std::endl;

    //encode the input massage and prepare it for sending
    mapid = argv[1][0];
    srcVtxid = atoi(argv[2]);
    dstVtxid = atoi(argv[3]);
    filesize = atoi(argv[4]);

    buf[0] = mapid;
    memcpy(buf+1, &srcVtxid, sizeof(int));
    memcpy(buf+1+sizeof(int), &dstVtxid, sizeof(int));
    memcpy(buf+1+2*sizeof(int), &filesize, sizeof(int));

    //send the encoded massage to AWS
    if (send(TCPfd, buf, 1+3*sizeof(int), 0) == -1)
    {
        perror("send");
        exit(1);
    }

    //The following massage on the screen means the end of phase 1.
    std::cout << "The client has sent query to AWS using TCP:\n* start vertex " << srcVtxid << ";\n* destination vertex " << dstVtxid << ";\n* map " << mapid
     << ";\n* file size " << filesize << "\n" << std::endl;

    if ((numbytes = recv(TCPfd, buf, MAXDATASIZE-1, 0)) == -1) 
    {
        perror("recv");
        exit(1);
    }
    if(buf[0] == 'y')
    {
        memcpy(&mindistan, buf + 1                  , sizeof(float));
        memcpy(&Tt       , buf + 1 + sizeof(float)  , sizeof(float));
        memcpy(&Tp       , buf + 1 + sizeof(float)*2, sizeof(float));
        memcpy(path      , buf + 1 + sizeof(float)*3, sizeof(path));
        std::cout << "The Client has received results from aws:" <<  std::endl;
        std::cout << "--------------------------------------------------------------------------------" << std::endl;
        std::cout << "Source \tDestination \tMin Length \tTt \t\tTp \t\tDelay" <<  std::endl;
        std::cout << "--------------------------------------------------------------------------------" << std::endl;
        std::cout << srcVtxid << " \t" << dstVtxid << " \t\t" << mindistan << " \t" << Tt << " \t" << Tp << " \t" << (Tt+Tp) << std::endl;
        std::cout << "--------------------------------------------------------------------------------" << std::endl;
        std::cout << "Shortest path: ";
        for (int i =0 ; i< 11; i++)
        {
            if(path[i] == 2333)
                break;
            
            if (i==0)
                std::cout << path[i];
            else
                std::cout << " -- " << path[i];

        }
        std::cout << std::endl;
    }
    else if(buf[0] == '!')
    {
        if(buf[1] == 'm')
        {
            std::cout << "No map id " << mapid << " found" << std::endl;
        }
        else if(buf[1] == 's')
        {
            std::cout << "No Vertex id " << srcVtxid << " found" << std::endl;
        }
        else if(buf[1] == 'd')
        {
            std::cout << "No Vertex id " << dstVtxid << " found" << std::endl;
        }
        else if(buf[1] == 'b')
        {
            std::cout << "Both Vertex id " << srcVtxid << " and Vertex id " << dstVtxid << " not found" << std::endl;
        }
    }

    close(TCPfd);
    return 0;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x468, %rsp            # imm = 0x468
cmpl $0x5, %edi
jne 0x1a11
movq %rsi, %r14
xorps %xmm0, %xmm0
leaq 0x50(%rsp), %rdx
movaps %xmm0, (%rdx)
movaps %xmm0, 0x20(%rdx)
movaps %xmm0, 0x10(%rdx)
movl $0x1, 0x8(%rdx)
leaq 0xcc1(%rip), %rdi       # 0x203b
leaq 0xcc4(%rip), %rsi       # 0x2045
leaq 0x10(%rsp), %rcx
callq 0x10e0
testl %eax, %eax
jne 0x192a
movq 0x10(%rsp), %r15
testq %r15, %r15
je 0x13f2
leaq 0xcb8(%rip), %r12       # 0x205c
leaq 0xcc0(%rip), %r13       # 0x206b
movl 0x4(%r15), %edi
movl 0x8(%r15), %esi
movl 0xc(%r15), %edx
callq 0x1040
movq %r12, %rdi
cmpl $-0x1, %eax
je 0x13e4
movl %eax, %ebx
movq 0x18(%r15), %rsi
movl 0x10(%r15), %edx
movl %eax, %edi
callq 0x1080
cmpl $-0x1, %eax
jne 0x1401
movl %ebx, %edi
callq 0x1170
movq %r13, %rdi
callq 0x1090
movq 0x28(%r15), %r15
testq %r15, %r15
jne 0x13ab
callq 0x1205
movl $0x2, %eax
jmp 0x19ff
movq 0x10(%rsp), %rdi
callq 0x10f0
movq 0x2bbe(%rip), %r15      # 0x3fd0
leaq 0xc7d(%rip), %rsi       # 0x2096
movl $0x1c, %edx
movq %r15, %rdi
callq 0x10c0
leaq 0xc0c(%rip), %rsi       # 0x2039
movl $0x1, %edx
movq %r15, %rdi
callq 0x10c0
movq (%r15), %rax
movq -0x18(%rax), %rdi
addq %r15, %rdi
movl $0xa, %esi
callq 0x10b0
movsbl %al, %esi
movq %r15, %rdi
callq 0x1030
movq %rax, %rdi
callq 0x1070
movq 0x8(%r14), %rax
movq 0x10(%r14), %rdi
movb (%rax), %bpl
callq 0x1130
movl %eax, %r13d
movq 0x18(%r14), %rdi
callq 0x1130
movl %eax, %r15d
movq 0x20(%r14), %rdi
callq 0x1130
movl %eax, %r12d
leaq 0x80(%rsp), %rsi
movb %bpl, (%rsi)
movl %r13d, 0x1(%rsi)
movl %r15d, 0x5(%rsi)
movl %eax, 0x9(%rsi)
movl $0xd, %edx
movl %ebx, %edi
xorl %ecx, %ecx
callq 0x1060
cmpq $-0x1, %rax
je 0x1a16
movq 0x2b0f(%rip), %r14      # 0x3fd0
leaq 0xbf0(%rip), %rsi       # 0x20b8
movl $0x3b, %edx
movq %r14, %rdi
callq 0x10c0
movq %r14, %rdi
movl %r13d, 0xc(%rsp)
movl %r13d, %esi
callq 0x1150
movq %rax, %r13
leaq 0xc05(%rip), %rsi       # 0x20f4
movl $0x17, %edx
movq %rax, %rdi
callq 0x10c0
movq %r13, %rdi
movl %r15d, (%rsp)
movl %r15d, %esi
callq 0x1150
movq %rax, %r13
leaq 0xbf7(%rip), %rsi       # 0x210c
movl $0x8, %edx
movq %rax, %rdi
callq 0x10c0
leaq 0x20(%rsp), %rsi
movl %ebp, %r15d
movb %bpl, (%rsi)
movl $0x1, %edx
movq %r13, %rdi
callq 0x10c0
movq %rax, %r13
leaq 0xbd1(%rip), %rsi       # 0x2115
movl $0xe, %edx
movq %rax, %rdi
callq 0x10c0
movq %r13, %rdi
movl %r12d, %esi
callq 0x1150
movq %rax, %r12
leaq 0xad3(%rip), %rsi       # 0x2039
movl $0x1, %edx
movq %rax, %rdi
callq 0x10c0
movq (%r12), %rax
movq -0x18(%rax), %rdi
addq %r12, %rdi
movl $0xa, %esi
callq 0x10b0
movsbl %al, %esi
movq %r12, %rdi
callq 0x1030
movq %rax, %rdi
callq 0x1070
leaq 0x80(%rsp), %rsi
movl $0x3e7, %edx            # imm = 0x3E7
movl %ebx, %edi
xorl %ecx, %ecx
callq 0x1050
cmpl $-0x1, %eax
je 0x1a1b
movzbl 0x80(%rsp), %eax
cmpl $0x21, %eax
movl 0xc(%rsp), %ebp
je 0x189e
cmpl $0x79, %eax
jne 0x19f6
movss 0x85(%rsp), %xmm0
movss %xmm0, 0x8(%rsp)
movss 0x89(%rsp), %xmm0
movss %xmm0, 0x4(%rsp)
movups 0x8d(%rsp), %xmm0
movaps %xmm0, 0x20(%rsp)
movups 0x9d(%rsp), %xmm0
movaps %xmm0, 0x30(%rsp)
movups 0xa9(%rsp), %xmm0
movups %xmm0, 0x3c(%rsp)
xorps %xmm0, %xmm0
cvtss2sd 0x81(%rsp), %xmm0
movsd %xmm0, 0x18(%rsp)
leaq 0xaf3(%rip), %rsi       # 0x2129
movl $0x29, %edx
movq %r14, %rdi
callq 0x10c0
movq (%r14), %rax
movq -0x18(%rax), %rdi
addq %r14, %rdi
movl $0xa, %esi
callq 0x10b0
movsbl %al, %esi
movq %r14, %rdi
callq 0x1030
movq %rax, %rdi
callq 0x1070
leaq 0xae2(%rip), %r12       # 0x2153
movl $0x50, %edx
movq %r14, %rdi
movq %r12, %rsi
callq 0x10c0
movq (%r14), %rax
movq -0x18(%rax), %rdi
addq %r14, %rdi
movl $0xa, %esi
callq 0x10b0
movsbl %al, %esi
movq %r14, %rdi
callq 0x1030
movq %rax, %rdi
callq 0x1070
leaq 0xaf5(%rip), %rsi       # 0x21a4
movl $0x30, %edx
movq %r14, %rdi
callq 0x10c0
movq (%r14), %rax
movq -0x18(%rax), %rdi
addq %r14, %rdi
movl $0xa, %esi
callq 0x10b0
movsbl %al, %esi
movq %r14, %rdi
callq 0x1030
movq %rax, %rdi
callq 0x1070
movl $0x50, %edx
movq %r14, %rdi
movq %r12, %rsi
callq 0x10c0
movq (%r14), %rax
movq -0x18(%rax), %rdi
addq %r14, %rdi
movl $0xa, %esi
callq 0x10b0
movsbl %al, %esi
movq %r14, %rdi
callq 0x1030
movq %rax, %rdi
callq 0x1070
movq %r14, %rdi
movl %ebp, %esi
callq 0x1150
movq %rax, %r13
leaq 0xaa7(%rip), %r15       # 0x21d5
movl $0x2, %edx
movq %rax, %rdi
movq %r15, %rsi
callq 0x10c0
movq %r13, %rdi
movl (%rsp), %esi
callq 0x1150
movq %rax, %r13
leaq 0xa85(%rip), %rsi       # 0x21d8
movl $0x3, %edx
movq %rax, %rdi
callq 0x10c0
movq %r13, %rdi
movsd 0x18(%rsp), %xmm0
callq 0x1140
movq %rax, %r13
movl $0x2, %edx
movq %rax, %rdi
movq %r15, %rsi
callq 0x10c0
xorps %xmm0, %xmm0
cvtss2sd 0x8(%rsp), %xmm0
movq %r13, %rdi
callq 0x1140
movq %rax, %r13
movl $0x2, %edx
movq %rax, %rdi
movq %r15, %rsi
callq 0x10c0
xorps %xmm0, %xmm0
cvtss2sd 0x4(%rsp), %xmm0
movq %r13, %rdi
callq 0x1140
movq %rax, %r13
movl $0x2, %edx
movq %rax, %rdi
movq %r15, %rsi
callq 0x10c0
movss 0x8(%rsp), %xmm0
addss 0x4(%rsp), %xmm0
cvtss2sd %xmm0, %xmm0
movq %r13, %rdi
callq 0x1140
movq %rax, %r15
movq (%rax), %rax
movq -0x18(%rax), %rdi
addq %r15, %rdi
movl $0xa, %esi
callq 0x10b0
movsbl %al, %esi
movq %r15, %rdi
callq 0x1030
movq %rax, %rdi
callq 0x1070
movl $0x50, %edx
movq %r14, %rdi
movq %r12, %rsi
callq 0x10c0
movq (%r14), %rax
movq -0x18(%rax), %rdi
addq %r14, %rdi
movl $0xa, %esi
callq 0x10b0
movsbl %al, %esi
movq %r14, %rdi
callq 0x1030
movq %rax, %rdi
callq 0x1070
leaq 0x993(%rip), %rsi       # 0x21dc
movl $0xf, %edx
movq %r14, %rdi
callq 0x10c0
xorl %r12d, %r12d
leaq 0x98c(%rip), %r15       # 0x21ec
movl 0x20(%rsp,%r12,4), %ebp
cmpl $0x91d, %ebp            # imm = 0x91D
je 0x19cf
testq %r12, %r12
je 0x1886
movl $0x4, %edx
movq %r14, %rdi
movq %r15, %rsi
callq 0x10c0
movq %r14, %rdi
movl %ebp, %esi
callq 0x1150
incq %r12
cmpq $0xb, %r12
jne 0x1860
jmp 0x19cf
movzbl 0x81(%rsp), %eax
cmpl $0x6c, %eax
jg 0x18e3
cmpl $0x62, %eax
je 0x193b
cmpl $0x64, %eax
jne 0x19f6
movq 0x270c(%rip), %r14      # 0x3fd0
leaq 0x931(%rip), %rsi       # 0x21fc
movl $0xd, %edx
movq %r14, %rdi
callq 0x10c0
movq %r14, %rdi
movl (%rsp), %esi
jmp 0x19b3
cmpl $0x73, %eax
je 0x1993
cmpl $0x6d, %eax
jne 0x19f6
movq 0x26d4(%rip), %r14      # 0x3fd0
leaq 0x8ee(%rip), %rsi       # 0x21f1
movl $0xa, %edx
movq %r14, %rdi
callq 0x10c0
leaq 0x20(%rsp), %rsi
movb %r15b, (%rsi)
movl $0x1, %edx
movq %r14, %rdi
callq 0x10c0
jmp 0x19b8
movl %eax, %edi
callq 0x11b5
movl $0x1, %eax
jmp 0x19ff
movq 0x268e(%rip), %r14      # 0x3fd0
leaq 0x8c1(%rip), %rsi       # 0x220a
movl $0xf, %edx
movq %r14, %rdi
callq 0x10c0
movq %r14, %rdi
movl %ebp, %esi
callq 0x1150
movq %rax, %r14
leaq 0x8b0(%rip), %rsi       # 0x221a
movl $0xf, %edx
movq %rax, %rdi
callq 0x10c0
movq %r14, %rdi
movl (%rsp), %esi
callq 0x1150
movq %rax, %r14
leaq 0x89e(%rip), %rsi       # 0x222a
movl $0xa, %edx
jmp 0x19c7
movq 0x2636(%rip), %r14      # 0x3fd0
leaq 0x85b(%rip), %rsi       # 0x21fc
movl $0xd, %edx
movq %r14, %rdi
callq 0x10c0
movq %r14, %rdi
movl %ebp, %esi
callq 0x1150
movq %rax, %r14
leaq 0x86c(%rip), %rsi       # 0x222e
movl $0x6, %edx
movq %rax, %rdi
callq 0x10c0
movq (%r14), %rax
movq -0x18(%rax), %rdi
addq %r14, %rdi
movl $0xa, %esi
callq 0x10b0
movsbl %al, %esi
movq %r14, %rdi
callq 0x1030
movq %rax, %rdi
callq 0x1070
movl %ebx, %edi
callq 0x1170
xorl %eax, %eax
addq $0x468, %rsp            # imm = 0x468
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
callq 0x1190
callq 0x11f0
callq 0x11db