void Properties::load()

in activemq-cpp/src/main/decaf/util/Properties.cpp [339:499]


void Properties::load(decaf::io::InputStream* stream) {

    try{

        if (stream == NULL) {
            throw NullPointerException(
                __FILE__, __LINE__, "The Stream instance passed was Null");
        }

        int mode = PARSE_MODE_NONE;
        char nextChar;
        std::vector<char> buf;
        int offset = 0;
        int keyLength = -1;
        int intVal;
        bool firstChar = true;
        BufferedInputStream bis(stream);

        while (true) {

            intVal = bis.read();

            if (intVal == -1) {
                break;
            }

            nextChar = (char) (intVal & 0xFF);

            if (mode == PARSE_MODE_SLASH) {

                mode = PARSE_MODE_NONE;
                switch( nextChar ) {
                    case '\r':
                        mode = PARSE_MODE_CONTINUE; // Look for a following \n
                        continue;
                    case '\n':
                        mode = PARSE_MODE_IGNORE; // Ignore whitespace on the next line
                        continue;
                    case 'b':
                        nextChar = '\b';
                        break;
                    case 'f':
                        nextChar = '\f';
                        break;
                    case 'n':
                        nextChar = '\n';
                        break;
                    case 'r':
                        nextChar = '\r';
                        break;
                    case 't':
                        nextChar = '\t';
                        break;
                }

            } else {

                switch( nextChar ) {
                    case '#':
                    case '!':
                        if (firstChar) {
                            while (true) {
                                intVal = bis.read();
                                if (intVal == -1) {
                                    break;
                                }

                                nextChar = (char) (intVal & 0xFF);

                                if (nextChar == '\r' || nextChar == '\n') {
                                    break;
                                }
                            }
                            continue;
                        }
                        break;
                    case '\n':
                        if (mode == PARSE_MODE_CONTINUE) { // Part of a \r\n sequence
                            mode = PARSE_MODE_IGNORE; // Ignore whitespace on the next line
                            continue;
                        }
                        // Intentional fall into the next case
                    case '\r':
                        mode = PARSE_MODE_NONE;
                        firstChar = true;
                        if (offset > 0 || (offset == 0 && keyLength == 0)) {

                            if (keyLength == -1) {
                                keyLength = offset;
                            }
                            std::string temp(buf.begin(), buf.begin() + offset);

                            this->internal->properties.put(
                                temp.substr(0, (std::size_t) keyLength), temp.substr((std::size_t) keyLength));
                        }

                        keyLength = -1;
                        offset = 0;
                        buf.clear();
                        continue;
                    case '\\':
                        if (mode == PARSE_MODE_KEY_DONE) {
                            keyLength = offset;
                        }
                        mode = PARSE_MODE_SLASH;
                        continue;
                    case ':':
                    case '=':
                        if (keyLength == -1) { // if parsing the key
                            mode = PARSE_MODE_NONE;
                            keyLength = offset;
                            continue;
                        }
                        break;
                }

                if (Character::isWhitespace(nextChar)) {
                    if (mode == PARSE_MODE_CONTINUE) {
                        mode = PARSE_MODE_IGNORE;
                    }
                    // if key length == 0 or value length == 0
                    if (offset == 0 || offset == keyLength || mode == PARSE_MODE_IGNORE) {
                        continue;
                    }
                    if (keyLength == -1) { // if parsing the key
                        mode = PARSE_MODE_KEY_DONE;
                        continue;
                    }
                }

                if (mode == PARSE_MODE_IGNORE || mode == PARSE_MODE_CONTINUE) {
                    mode = PARSE_MODE_NONE;
                }
            }

            firstChar = false;
            if (mode == PARSE_MODE_KEY_DONE) {
                keyLength = offset;
                mode = PARSE_MODE_NONE;
            }

            offset += 1;
            buf.push_back(nextChar);
        }

        if (keyLength == -1 && offset > 0) {
            keyLength = offset;
        }

        if (keyLength >= 0) {
            std::string temp(buf.begin(), buf.begin() + offset);
            this->internal->properties.put(
                temp.substr(0, (std::size_t) keyLength), temp.substr((std::size_t) keyLength));
        }
    }
    DECAF_CATCH_RETHROW(IOException)
    DECAF_CATCH_RETHROW(IllegalArgumentException)
    DECAF_CATCH_RETHROW(NullPointerException)
    DECAF_CATCH_EXCEPTION_CONVERT(Exception, IOException)
    DECAF_CATCHALL_THROW(IOException)
}