SQL_QFO_FUNCTION_ATTRIBUTES short Sql_Qfo_Close(short quasi_file_number)
{
    CliGlobals *cliGlobals;
    if (QfoRevealSegs(cliGlobals) != 0)
        return 0;
    cliGlobals->setLogEmsEvents(FALSE);
    jmp_buf jmpBuf;
    cliGlobals->setJmpBufPtr(&jmpBuf);
    Int32 jmpRc = setjmp(jmpBuf);
    if (jmpRc)
    {
        cliGlobals->setLogEmsEvents(TRUE);
        QfoHideSegs(cliGlobals);
        return 0;
    }
    QuasiFileManager *quasiFileManager = cliGlobals->getQuasiFileManager();
    quasiFileManager->closeQuasiFile(quasi_file_number);
    cliGlobals->setLogEmsEvents(TRUE);
    QfoHideSegs(cliGlobals);
    return 0;
}
SQL_QFO_FUNCTION_ATTRIBUTES short Sql_Qfo_IOComp(short quasi_file_number /*in*/,
        Lng32 *tag /*out*/,
        unsigned short *waitmask /*out*/,
        short userstop /*in*/)
{
    short retVal, feError = FEOK;
    RETCODE retcode;
    QuasiFileManager *quasiFileManager;
    *waitmask = LDONE;
    CliGlobals *cliGlobals;
    if (QfoRevealSegs(cliGlobals) != 0)
        return FEBADPARMVALUE;
    jmp_buf jmpBuf;
    short oldStop;
    oldStop = SETSTOP(1);
    cliGlobals->setJmpBufPtr(&jmpBuf);
    Int32 jmpRc = setjmp(jmpBuf);
    if (jmpRc)
    {
        QfoHideSegs(cliGlobals);
        SETSTOP(oldStop);
        return FEBADPARMVALUE; // longjmp not associated with statement
    }
    quasiFileManager = cliGlobals->getQuasiFileManager();
    if (quasiFileManager->getPendingNowaitOps() > 0)
        retcode = quasiFileManager->awaitIox(quasi_file_number, tag, &feError);
    else
    {
        QfoHideSegs(cliGlobals);
        SETSTOP(oldStop);
        return FENONEOUT;
    }
    if (feError != FEOK)
        retVal = feError; // May be FEBADPARMVALUE, or FENONEOUT
    else
    {
        if (1) // Not used but is compiled on NT
            retVal = FEQFOEVENTCONSUMED;
        else
            switch (retcode)
            {
            case SUCCESS:
                retVal = FEOK;
                break;
            case ERROR:
                retVal = FESQLERR;
                break;
            case SQL_EOF:
            case WARNING:
                retVal = FESQLWARN;
                break;
            case NOT_FINISHED:
                retVal = FEQFONOTCOMPLETE;
                break;
            default:
                retVal = FEBADPARMVALUE;
            }
    }
    QfoHideSegs(cliGlobals);
    SETSTOP(oldStop);
    return retVal;
}
예제 #3
0
void runServer(Int32 argc, char **argv)
{
  Int32 shmid;
  jmp_buf sscpJmpBuf;
  StatsGlobals *statsGlobals = NULL;
  void *statsGlobalsAddr;
  NABoolean createStatsGlobals = FALSE;
  CliGlobals *cliGlobals = CliGlobals::createCliGlobals(FALSE);
  char tmbuf[64];
  time_t now;
  struct tm *nowtm;

  long maxSegSize = STATS_MAX_SEG_SIZE;
  char *envSegSize = getenv("MX_RTS_STATS_SEG_SIZE");
  if (envSegSize)
  {
    maxSegSize = (long) str_atoi(envSegSize, str_len(envSegSize));
    if (maxSegSize < 32)
      maxSegSize = 32;
    else if (maxSegSize > 256)
      maxSegSize = 256;
    maxSegSize *= 1024 * 1024;
  }
  long enableHugePages = 0;
  int shmFlag = RMS_SHMFLAGS;
  char *envShmHugePages = getenv("SQ_RMS_ENABLE_HUGEPAGES");
  if (envShmHugePages != NULL)
  {
     enableHugePages = (long) str_atoi(envShmHugePages,
                         str_len(envShmHugePages));
     if (enableHugePages > 0)
       shmFlag =  shmFlag | SHM_HUGETLB;
  }

  now = time(NULL);
  nowtm = localtime(&now);
  strftime(tmbuf, sizeof tmbuf, "%Y-%m-%d %H:%M:%S ", nowtm);

  if ((shmid = shmget((key_t)getStatsSegmentId(),
                         0,  // size doesn't matter unless we are creating.
                         shmFlag)) == -1)
  {
    if (errno == ENOENT)
    {
      // Normal case, segment does not exist yet. Try to create.
      bool didCreate = true;
      if ((shmid = shmget((key_t)getStatsSegmentId(),
                                maxSegSize,
                                shmFlag | IPC_CREAT)) == -1)
      {
        if (enableHugePages > 0)
        {
          enableHugePages = 0;
          // try again withouf hugepages
          shmFlag =  shmFlag & ~SHM_HUGETLB;
          if ((shmid = shmget((key_t)getStatsSegmentId(),
                                    maxSegSize,
                                    shmFlag | IPC_CREAT)) == -1)
            didCreate = false;
        }
        else 
          didCreate = false;
      }

      if (didCreate)
      {
        cout << tmbuf 
             << " RMS Shared segment id = " 
             << shmid << ", key = " 
             << (key_t)getStatsSegmentId() ;
        if (enableHugePages > 0)
          cout << ", created with huge pages support." << endl;
        else
          cout << ", created without huge pages support." << endl;

        createStatsGlobals = TRUE;
      }
      else
      {
        cout << tmbuf
             << " Shmget failed, key = "
             << getStatsSegmentId()
             <<", Error code: "
             << errno
             << " ("
             << strerror(errno)
             << ")" << endl;
        exit(errno);
      }
    } // if ENOENT (i.e., attempting creation.)
  }
  else
  {
     cout << tmbuf << " RMS Shared segment exists, attaching to it, shmid="<< shmid << ", key=" << (key_t)getStatsSegmentId() << "\n";
  }
  if ((statsGlobalsAddr = shmat(shmid, getRmsSharedMemoryAddr(), 0))
		== (void *)-1)
  {
    cout << tmbuf << "Shmat failed, shmid=" <<shmid << ", key=" << (key_t) getStatsSegmentId() << ", Error code : "  << errno << "(" << strerror(errno) << ")\n";
    exit(errno);
  }
  char *statsGlobalsStartAddr = (char *)statsGlobalsAddr;
  if (createStatsGlobals)
  {
     short envType = StatsGlobals::RTS_GLOBAL_ENV;
     statsGlobals = new (statsGlobalsStartAddr)
             StatsGlobals((void *)statsGlobalsAddr, envType, maxSegSize);
     cliGlobals->setSharedMemId(shmid);
     // We really should not squirrel the statsGlobals pointer away like
     // this until the StatsGloblas is initialized, but
     // statsGlobals->init() needs it ......
     cliGlobals->setStatsGlobals(statsGlobals);
     statsGlobals->init();
  }
  else
  {
    statsGlobals = (StatsGlobals *)statsGlobalsAddr;
    cliGlobals->setSharedMemId(shmid);
    cliGlobals->setStatsGlobals(statsGlobals);
  }
  XPROCESSHANDLE_GETMINE_(statsGlobals->getSscpProcHandle());
  NAHeap *sscpHeap = cliGlobals->getExecutorMemory();
  cliGlobals->setJmpBufPtr(&sscpJmpBuf);
  if (setjmp(sscpJmpBuf))
    NAExit(1); // Abend
  IpcEnvironment  *sscpIpcEnv = new (sscpHeap) IpcEnvironment(sscpHeap, cliGlobals->getEventConsumed(),
      FALSE, IPC_SQLSSCP_SERVER, FALSE, TRUE);

  SscpGlobals *sscpGlobals = NULL;

  sscpGlobals = new (sscpHeap) SscpGlobals(sscpHeap, statsGlobals);

  // Currently open $RECEIVE with 256
  SscpGuaReceiveControlConnection *cc =
	 new(sscpHeap) SscpGuaReceiveControlConnection(sscpIpcEnv,
					  sscpGlobals,
                                           256);
  sscpIpcEnv->setControlConnection(cc);
  while (TRUE)
  {
     while (cc->getConnection() == NULL)
      cc->wait(IpcInfiniteTimeout);

#ifdef _DEBUG_RTS
    cerr << "No. of Requesters-1 "  << cc->getNumRequestors() << " \n";
#endif
    while (cc->getNumRequestors() > 0)
    {
      sscpIpcEnv->getAllConnections()->waitOnAll(IpcInfiniteTimeout);
    } // Inner while
  }
}  // runServer