Optimize this by just dealing with nanos so as not to allocate extra objects, like this:

    int nanos = PDataType.INTEGER.getCodec().decodeInt(ptr.getBuffer(),ptr.getOffset()+PDataType.LONG.getMaxLength()); // Skip ms part
    if (nanos / divBy >= HALF_OF_NANOS_IN_MILLI ) {
        // Get millisecond timestamp value using codec to prevent object allocation
        long ts = (getDataType() == PDataType.TIMESTAMP ? PDataType.LONG : PDataType.UNSIGNED_LONG).getCodec().decodeLong(ptr.getBuffer(),ptr.getOffset());
        Timestamp roundedTs = new Timestamp(ts.getTime() + 1);
        byte[] byteValue = getDataType().toBytes(roundedTs);
        ptr.set(byteValue);
    }
    return true; // Otherwise, just return with the eval of the first child, as this is the correct value