// File: /workspace/github_c_makefile_star2_O3/umbrant[P]Non-blocking-Buffers/nbb.c
// Function: nbb_init_service
int nbb_init_service(int num_channels, const char* name) 
{
  char request[MAX_MSG_LEN] = {};
  char num_channel[2]; // TODO: Make it constants?
  char pid[PID_MAX_STRLEN + 1];

  assert(num_channels > 0 && name != NULL);

  sem_id = sem_open(SEM_KEY, 0);
  if(sem_id == SEM_FAILED) {
    perror("! nbb_init_service(): Unable to obtain semaphore\n");
    return -1;
  }

  // BEGIN CRITICAL SECTION
  //TODO: sem_wait(sem_id);

  sprintf(num_channel, "%d", num_channels);
  sprintf(pid, "%d", getpid());

  strcpy(request, SERVICE);
  strcat(request, " ");
  strcat(request, name);
  strcat(request, " ");
  strcat(request, num_channel); 
  strcat(request, " ");
  strcat(request, pid);

  printf("request: %s, len: %zu\n", request, strlen(request));

  char* recv;
  int recv_len;
  
  if(nbb_nameserver_connect(request, &recv, &recv_len)) {
    printf("! nbb_init_service(): Could not connect to nameserver\n");
    sem_post(sem_id);
    return -1;
  }

  if(!strcmp(recv, NAMESERVER_CHANNEL_FULL)) {
    printf("! nbb_init_service(): Reserving channel unsuccessful\n");
  
    sem_post(sem_id);
    return -1;
  }
  else {
    printf("recv (%d): %.*s\n", recv_len, recv_len, recv);
    printf("** Acquired the following channels: %.*s\n", recv_len, recv);

    int i;
    int channel;
    char* tmp;

    tmp = strtok(recv, " ");
    for(i = 1;i <= num_channels;i++) { 
      channel = atoi(tmp);
      if(nbb_open_channel(name, channel, channel + READ_WRITE_CONV, IPC_CREAT) == -1) {
        //TODO: service_exit();
        printf("! nbb_init_service(): Failed to open the %d-th channel\n", i);
        sem_post(sem_id);
        free(recv);
        return -1;
      }
      tmp = strtok(NULL, " ");
    }

    signal(SIGUSR1, nbb_recv_data);

    sem_post(sem_id);
    free(recv);
    return 0;
  }
  // END CRITICAL SECTION
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x408, %rsp            # imm = 0x408
movq %rsi, %rbx
movl %edi, %r14d
leaq 0x20(%rsp), %rdi
movl $0x3e8, %edx            # imm = 0x3E8
xorl %esi, %esi
callq 0x10e0
testl %r14d, %r14d
jle 0x1ee5
testq %rbx, %rbx
je 0x1ee5
leaq 0x1515(%rip), %rdi      # 0x31d7
xorl %esi, %esi
xorl %eax, %eax
callq 0x1110
movq %rax, 0x4a8e(%rip)      # 0x6760
testq %rax, %rax
je 0x1ed4
leaq 0x133b(%rip), %r15      # 0x301d
leaq 0x18(%rsp), %r12
movq %r12, %rdi
movq %r15, %rsi
movl %r14d, %edx
xorl %eax, %eax
callq 0x1220
callq 0x1090
leaq 0x1a(%rsp), %r13
movq %r13, %rdi
movq %r15, %rsi
movl %eax, %edx
xorl %eax, %eax
callq 0x1220
leaq 0x20(%rsp), %r15
movw $0x30, (%r15)
movq %r15, %rdi
callq 0x10b0
movw $0x20, %bp
movw %bp, 0x20(%rsp,%rax)
movq %r15, %rdi
movq %rbx, %rsi
callq 0x1210
movq %r15, %rdi
callq 0x10b0
movw %bp, 0x20(%rsp,%rax)
movq %r15, %rdi
movq %r12, %rsi
callq 0x1210
movq %r15, %rdi
callq 0x10b0
movw %bp, 0x20(%rsp,%rax)
movq %r15, %rdi
movq %r13, %rsi
callq 0x1210
movq %r15, %rdi
callq 0x10b0
leaq 0x1503(%rip), %rdi      # 0x3279
movq %r15, %rsi
movq %rax, %rdx
xorl %eax, %eax
callq 0x10c0
leaq 0x8(%rsp), %rsi
leaq 0x14(%rsp), %rdx
movq %r15, %rdi
callq 0x161c
testl %eax, %eax
je 0x1dc8
leaq 0x1c06(%rip), %rdi      # 0x39a6
callq 0x1070
movq 0x49b4(%rip), %rdi      # 0x6760
callq 0x10f0
movl $0xffffffff, %eax       # imm = 0xFFFFFFFF
addq $0x408, %rsp            # imm = 0x408
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
movq 0x8(%rsp), %r15
leaq 0x1cdc(%rip), %rsi      # 0x3ab0
movq %r15, %rdi
callq 0x1100
testl %eax, %eax
je 0x1e9c
movl 0x14(%rsp), %edx
leaq 0x14a1(%rip), %rdi      # 0x3290
movl %edx, %esi
movq %r15, %rcx
xorl %eax, %eax
callq 0x10c0
movl 0x14(%rsp), %esi
movq 0x8(%rsp), %rdx
leaq 0x1496(%rip), %rdi      # 0x32a1
xorl %eax, %eax
callq 0x10c0
movq 0x8(%rsp), %rdi
leaq 0x127d(%rip), %r15      # 0x309b
movq %r15, %rsi
callq 0x11c0
negl %r14d
movl $0x1, %r12d
movq %rax, %rdi
callq 0x11f0
leal 0x3e8(%rax), %edx
movq %rbx, %rdi
movl %eax, %esi
movl $0x200, %ecx            # imm = 0x200
callq 0x173a
cmpl $-0x1, %eax
je 0x1ea8
xorl %edi, %edi
movq %r15, %rsi
callq 0x11c0
leal (%r14,%r12), %ecx
incl %ecx
movl %r12d, %edx
incl %edx
movl %edx, %r12d
cmpl $0x1, %ecx
jne 0x1e2f
leaq 0x8f(%rip), %rsi        # 0x1f04
movl $0xa, %edi
callq 0x1140
movq 0x48da(%rip), %rdi      # 0x6760
callq 0x10f0
movq 0x8(%rsp), %rdi
callq 0x1030
xorl %eax, %eax
jmp 0x1db6
leaq 0x1ace(%rip), %rdi      # 0x3971
jmp 0x1da0
leaq 0x141c(%rip), %rdi      # 0x32cb
movl %r12d, %esi
xorl %eax, %eax
callq 0x10c0
movq 0x48a0(%rip), %rdi      # 0x6760
callq 0x10f0
movq 0x8(%rsp), %rdi
callq 0x1030
jmp 0x1db1
leaq 0x136c(%rip), %rdi      # 0x3247
callq 0x11b0
jmp 0x1db1
leaq 0x1312(%rip), %rdi      # 0x31fe
leaq 0x12a2(%rip), %rsi      # 0x3195
leaq 0x1325(%rip), %rcx      # 0x321f
movl $0x56, %edx
callq 0x10d0