void tst_QScopedPointer::array()
{
    int instCount = RefCounted::instanceCount.load();
    {
        QScopedArrayPointer<RefCounted> array;
        array.reset(new RefCounted[42]);
        QCOMPARE(instCount + 42, RefCounted::instanceCount.load());
    }
    QCOMPARE(instCount, RefCounted::instanceCount.load());
    {
        QScopedArrayPointer<RefCounted> array(new RefCounted[42]);
        QCOMPARE(instCount + 42, RefCounted::instanceCount.load());
        array.reset(new RefCounted[28]);
        QCOMPARE(instCount + 28, RefCounted::instanceCount.load());
        array.reset(0);
        QCOMPARE(instCount, RefCounted::instanceCount.load());
    }
    QCOMPARE(instCount, RefCounted::instanceCount.load());
}
Example #2
0
// runProcess: Run a command line process (replacement for QProcess which
// does not exist in the bootstrap library).
bool runProcess(const QString &binary, const QStringList &args,
                const QString &workingDirectory,
                unsigned long *exitCode, QByteArray *stdOut, QByteArray *stdErr,
                QString *errorMessage)
{
    QScopedArrayPointer<char> stdOutFileName;
    QScopedArrayPointer<char> stdErrFileName;

    int stdOutFile = 0;
    if (stdOut) {
        stdOutFileName.reset(tempFilePattern());
        stdOutFile = mkstemp(stdOutFileName.data());
        if (stdOutFile < 0) {
            *errorMessage = QStringLiteral("mkstemp() failed: ") + QString::fromLocal8Bit(strerror(errno));
            return false;
        }
    }

    int stdErrFile = 0;
    if (stdErr) {
        stdErrFileName.reset(tempFilePattern());
        stdErrFile = mkstemp(stdErrFileName.data());
        if (stdErrFile < 0) {
            *errorMessage = QStringLiteral("mkstemp() failed: ") + QString::fromLocal8Bit(strerror(errno));
            return false;
        }
    }

    const pid_t pID = fork();

    if (pID < 0) {
        *errorMessage = QStringLiteral("Fork failed: ") + QString::fromLocal8Bit(strerror(errno));
        return false;
    }

    if (!pID) { // Child
        if (stdOut) {
            dup2(stdOutFile, STDOUT_FILENO);
            close(stdOutFile);
        }
        if (stdErr) {
            dup2(stdErrFile, STDERR_FILENO);
            close(stdErrFile);
        }

        if (!workingDirectory.isEmpty() && !QDir::setCurrent(workingDirectory)) {
            std::wcerr << "Failed to change working directory to " << workingDirectory << ".\n";
            ::_exit(-1);
        }

        char **argv  = new char *[args.size() + 2]; // Create argv.
        char **ap = argv;
        *ap++ = encodeFileName(binary);
        foreach (const QString &a, args)
            *ap++ = encodeFileName(a);
        *ap = 0;

        execvp(argv[0], argv);
        ::_exit(-1);
    }

    int status;
    pid_t waitResult;

    do {
        waitResult = waitpid(pID, &status, 0);
    } while (waitResult == -1 && errno == EINTR);

    if (stdOut) {
        *stdOut = readOutRedirectFile(stdOutFile);
        unlink(stdOutFileName.data());
    }
    if (stdErr) {
        *stdErr = readOutRedirectFile(stdErrFile);
        unlink(stdErrFileName.data());
    }

    if (waitResult < 0) {
        *errorMessage = QStringLiteral("Wait failed: ") + QString::fromLocal8Bit(strerror(errno));
        return false;
    }
    if (!WIFEXITED(status)) {
        *errorMessage = binary + QStringLiteral(" did not exit cleanly.");
        return false;
    }
    if (exitCode)
        *exitCode = WEXITSTATUS(status);
    return true;
}