Search in sources :

Example 46 with Page

use of org.h2.mvstore.Page in project h2database by h2database.

the class PageDataIndex method getPage.

/**
 * Read the given page.
 *
 * @param id the page id
 * @param parent the parent, or -1 if unknown
 * @return the page
 */
PageData getPage(int id, int parent) {
    Page pd = store.getPage(id);
    if (pd == null) {
        PageDataLeaf empty = PageDataLeaf.create(this, id, parent);
        // could have been created before, but never committed
        store.logUndo(empty, null);
        store.update(empty);
        return empty;
    } else if (!(pd instanceof PageData)) {
        throw DbException.get(ErrorCode.FILE_CORRUPTED_1, "" + pd);
    }
    PageData p = (PageData) pd;
    if (parent != -1) {
        if (p.getParentPageId() != parent) {
            throw DbException.throwInternalError(p + " parent " + p.getParentPageId() + " expected " + parent);
        }
    }
    return p;
}
Also used : Page(org.h2.store.Page)

Example 47 with Page

use of org.h2.mvstore.Page in project h2database by h2database.

the class PageDataLeaf method getRowAt.

/**
 * Get the row at the given index.
 *
 * @param at the index
 * @return the row
 */
Row getRowAt(int at) {
    Row r = rows[at];
    if (r == null) {
        if (firstOverflowPageId == 0) {
            r = readRow(data, offsets[at], columnCount);
        } else {
            if (rowRef != null) {
                r = rowRef.get();
                if (r != null) {
                    return r;
                }
            }
            PageStore store = index.getPageStore();
            Data buff = store.createData();
            int pageSize = store.getPageSize();
            int offset = offsets[at];
            buff.write(data.getBytes(), offset, pageSize - offset);
            int next = firstOverflowPageId;
            do {
                PageDataOverflow page = index.getPageOverflow(next);
                next = page.readInto(buff);
            } while (next != 0);
            overflowRowSize = pageSize + buff.length();
            r = readRow(buff, 0, columnCount);
        }
        r.setKey(keys[at]);
        if (firstOverflowPageId != 0) {
            rowRef = new SoftReference<>(r);
        } else {
            rows[at] = r;
            memoryChange(true, r);
        }
    }
    return r;
}
Also used : PageStore(org.h2.store.PageStore) Data(org.h2.store.Data) Row(org.h2.result.Row)

Example 48 with Page

use of org.h2.mvstore.Page in project h2database by h2database.

the class PageDataLeaf method addRowTry.

@Override
int addRowTry(Row row) {
    index.getPageStore().logUndo(this, data);
    int rowLength = getRowLength(row);
    int pageSize = index.getPageStore().getPageSize();
    int last = entryCount == 0 ? pageSize : offsets[entryCount - 1];
    int keyOffsetPairLen = 2 + Data.getVarLongLen(row.getKey());
    if (entryCount > 0 && last - rowLength < start + keyOffsetPairLen) {
        int x = findInsertionPoint(row.getKey());
        if (entryCount > 1) {
            if (entryCount < 5) {
                // required, otherwise the index doesn't work correctly
                return entryCount / 2;
            }
            if (index.isSortedInsertMode()) {
                return x < 2 ? 1 : x > entryCount - 1 ? entryCount - 1 : x;
            }
            // split near the insertion point to better fill pages
            // split in half would be:
            // return entryCount / 2;
            int third = entryCount / 3;
            return x < third ? third : x >= 2 * third ? 2 * third : x;
        }
        return x;
    }
    index.getPageStore().logUndo(this, data);
    int x;
    if (entryCount == 0) {
        x = 0;
    } else {
        if (!optimizeUpdate) {
            readAllRows();
        }
        x = findInsertionPoint(row.getKey());
    }
    written = false;
    changeCount = index.getPageStore().getChangeCount();
    last = x == 0 ? pageSize : offsets[x - 1];
    int offset = last - rowLength;
    start += keyOffsetPairLen;
    offsets = insert(offsets, entryCount, x, offset);
    add(offsets, x + 1, entryCount + 1, -rowLength);
    keys = insert(keys, entryCount, x, row.getKey());
    rows = insert(rows, entryCount, x, row);
    entryCount++;
    index.getPageStore().update(this);
    if (optimizeUpdate) {
        if (writtenData && offset >= start) {
            byte[] d = data.getBytes();
            int dataStart = offsets[entryCount - 1] + rowLength;
            int dataEnd = offsets[x];
            System.arraycopy(d, dataStart, d, dataStart - rowLength, dataEnd - dataStart + rowLength);
            data.setPos(dataEnd);
            for (int j = 0; j < columnCount; j++) {
                data.writeValue(row.getValue(j));
            }
        }
    }
    if (offset < start) {
        writtenData = false;
        if (entryCount > 1) {
            DbException.throwInternalError("" + entryCount);
        }
        // need to write the overflow page id
        start += 4;
        int remaining = rowLength - (pageSize - start);
        // fix offset
        offset = start;
        offsets[x] = offset;
        int previous = getPos();
        int dataOffset = pageSize;
        int page = index.getPageStore().allocatePage();
        firstOverflowPageId = page;
        this.overflowRowSize = pageSize + rowLength;
        writeData();
        // free up the space used by the row
        Row r = rows[0];
        rowRef = new SoftReference<>(r);
        rows[0] = null;
        Data all = index.getPageStore().createData();
        all.checkCapacity(data.length());
        all.write(data.getBytes(), 0, data.length());
        data.truncate(index.getPageStore().getPageSize());
        do {
            int type, size, next;
            if (remaining <= pageSize - PageDataOverflow.START_LAST) {
                type = Page.TYPE_DATA_OVERFLOW | Page.FLAG_LAST;
                size = remaining;
                next = 0;
            } else {
                type = Page.TYPE_DATA_OVERFLOW;
                size = pageSize - PageDataOverflow.START_MORE;
                next = index.getPageStore().allocatePage();
            }
            PageDataOverflow overflow = PageDataOverflow.create(index.getPageStore(), page, type, previous, next, all, dataOffset, size);
            index.getPageStore().update(overflow);
            dataOffset += size;
            remaining -= size;
            previous = page;
            page = next;
        } while (remaining > 0);
    }
    if (rowRef == null) {
        memoryChange(true, row);
    } else {
        memoryChange(true, null);
    }
    return -1;
}
Also used : Data(org.h2.store.Data) Row(org.h2.result.Row)

Example 49 with Page

use of org.h2.mvstore.Page in project h2database by h2database.

the class PageDataOverflow method moveTo.

@Override
public void moveTo(Session session, int newPos) {
    // load the pages into the cache, to ensure old pages
    // are written
    Page parent = store.getPage(parentPageId);
    if (parent == null) {
        throw DbException.throwInternalError();
    }
    PageDataOverflow next = null;
    if (nextPage != 0) {
        next = (PageDataOverflow) store.getPage(nextPage);
    }
    store.logUndo(this, data);
    PageDataOverflow p2 = PageDataOverflow.create(store, newPos, type, parentPageId, nextPage, data, start, size);
    store.update(p2);
    if (next != null) {
        next.setParentPageId(newPos);
        store.update(next);
    }
    if (parent instanceof PageDataOverflow) {
        PageDataOverflow p1 = (PageDataOverflow) parent;
        p1.setNext(getPos(), newPos);
    } else {
        PageDataLeaf p1 = (PageDataLeaf) parent;
        p1.setOverflow(getPos(), newPos);
    }
    store.update(parent);
    store.free(getPos());
}
Also used : Page(org.h2.store.Page)

Example 50 with Page

use of org.h2.mvstore.Page in project h2database by h2database.

the class Server method openBrowser.

/**
 * Open a new browser tab or window with the given URL.
 *
 * @param url the URL to open
 */
public static void openBrowser(String url) throws Exception {
    try {
        String osName = StringUtils.toLowerEnglish(Utils.getProperty("os.name", "linux"));
        Runtime rt = Runtime.getRuntime();
        String browser = Utils.getProperty(SysProperties.H2_BROWSER, null);
        if (browser == null) {
            // under Linux, this will point to the default system browser
            try {
                browser = System.getenv("BROWSER");
            } catch (SecurityException se) {
            // ignore
            }
        }
        if (browser != null) {
            if (browser.startsWith("call:")) {
                browser = browser.substring("call:".length());
                Utils.callStaticMethod(browser, url);
            } else if (browser.contains("%url")) {
                String[] args = StringUtils.arraySplit(browser, ',', false);
                for (int i = 0; i < args.length; i++) {
                    args[i] = StringUtils.replaceAll(args[i], "%url", url);
                }
                rt.exec(args);
            } else if (osName.contains("windows")) {
                rt.exec(new String[] { "cmd.exe", "/C", browser, url });
            } else {
                rt.exec(new String[] { browser, url });
            }
            return;
        }
        try {
            Class<?> desktopClass = Class.forName("java.awt.Desktop");
            // Desktop.isDesktopSupported()
            Boolean supported = (Boolean) desktopClass.getMethod("isDesktopSupported").invoke(null, new Object[0]);
            URI uri = new URI(url);
            if (supported) {
                // Desktop.getDesktop();
                Object desktop = desktopClass.getMethod("getDesktop").invoke(null);
                // desktop.browse(uri);
                desktopClass.getMethod("browse", URI.class).invoke(desktop, uri);
                return;
            }
        } catch (Exception e) {
        // ignore
        }
        if (osName.contains("windows")) {
            rt.exec(new String[] { "rundll32", "url.dll,FileProtocolHandler", url });
        } else if (osName.contains("mac") || osName.contains("darwin")) {
            // Mac OS: to open a page with Safari, use "open -a Safari"
            Runtime.getRuntime().exec(new String[] { "open", url });
        } else {
            String[] browsers = { "xdg-open", "chromium", "google-chrome", "firefox", "mozilla-firefox", "mozilla", "konqueror", "netscape", "opera", "midori" };
            boolean ok = false;
            for (String b : browsers) {
                try {
                    rt.exec(new String[] { b, url });
                    ok = true;
                    break;
                } catch (Exception e) {
                // ignore and try the next
                }
            }
            if (!ok) {
                // No success in detection.
                throw new Exception("Browser detection failed and system property " + SysProperties.H2_BROWSER + " not set");
            }
        }
    } catch (Exception e) {
        throw new Exception("Failed to start a browser to open the URL " + url + ": " + e.getMessage());
    }
}
Also used : URI(java.net.URI) DbException(org.h2.message.DbException) SQLException(java.sql.SQLException)

Aggregations

CreateTableData (org.h2.command.ddl.CreateTableData)8 Page (org.h2.mvstore.Page)7 Data (org.h2.store.Data)7 Column (org.h2.table.Column)5 IndexColumn (org.h2.table.IndexColumn)5 Value (org.h2.value.Value)5 MVStore (org.h2.mvstore.MVStore)4 Row (org.h2.result.Row)4 SearchRow (org.h2.result.SearchRow)4 IOException (java.io.IOException)3 Connection (java.sql.Connection)3 CRC32 (java.util.zip.CRC32)3 PageBtreeIndex (org.h2.index.PageBtreeIndex)3 PageDataIndex (org.h2.index.PageDataIndex)3 PageIndex (org.h2.index.PageIndex)3 DbException (org.h2.message.DbException)3 Page (org.h2.store.Page)3 ValueString (org.h2.value.ValueString)3 PrintWriter (java.io.PrintWriter)2 ResultSet (java.sql.ResultSet)2