diff --git a/src/core/org/luaj/vm2/LuaString.java b/src/core/org/luaj/vm2/LuaString.java index 2c3e8869..08c1022b 100644 --- a/src/core/org/luaj/vm2/LuaString.java +++ b/src/core/org/luaj/vm2/LuaString.java @@ -31,28 +31,28 @@ import java.io.PrintStream; import org.luaj.vm2.lib.MathLib; /** - * Subclass of {@link LuaValue} for representing lua strings. + * Subclass of {@link LuaValue} for representing lua strings. *
- * Because lua string values are more nearly sequences of bytes than + * Because lua string values are more nearly sequences of bytes than * sequences of characters or unicode code points, the {@link LuaString} - * implementation holds the string value in an internal byte array. + * implementation holds the string value in an internal byte array. *
- * {@link LuaString} values are not considered mutable once constructed, + * {@link LuaString} values are not considered mutable once constructed, * so multiple {@link LuaString} values can chare a single byte array. *
* Currently {@link LuaString}s are pooled via a centrally managed weak table. - * To ensure that as many string values as possible take advantage of this, - * Constructors are not exposed directly. As with number, booleans, and nil, + * To ensure that as many string values as possible take advantage of this, + * Constructors are not exposed directly. As with number, booleans, and nil, * instance construction should be via {@link LuaValue#valueOf(byte[])} or similar API. *
* Because of this pooling, users of LuaString must not directly alter the * bytes in a LuaString, or undefined behavior will result. *
- * When Java Strings are used to initialize {@link LuaString} data, the UTF8 encoding is assumed. - * The functions + * When Java Strings are used to initialize {@link LuaString} data, the UTF8 encoding is assumed. + * The functions * {@link #lengthAsUtf8(char[])}, - * {@link #encodeToUtf8(char[], int, byte[], int)}, and - * {@link #decodeAsUtf8(byte[], int, int)} + * {@link #encodeToUtf8(char[], int, byte[], int)}, and + * {@link #decodeAsUtf8(byte[], int, int)} * are used to convert back and forth between UTF8 byte arrays and character arrays. * * @see LuaValue @@ -63,15 +63,15 @@ public class LuaString extends LuaValue { /** The singleton instance for string metatables that forwards to the string functions. * Typically, this is set to the string metatable as a side effect of loading the string - * library, and is read-write to provide flexible behavior by default. When used in a + * library, and is read-write to provide flexible behavior by default. When used in a * server environment where there may be roge scripts, this should be replaced with a * read-only table since it is shared across all lua code in this Java VM. */ public static LuaValue s_metatable; /** The bytes for the string. These must not be mutated directly because - * the backing may be shared by multiple LuaStrings, and the hash code is - * computed only at construction time. + * the backing may be shared by multiple LuaStrings, and the hash code is + * computed only at construction time. * It is exposed only for performance and legacy reasons. */ public final byte[] m_bytes; @@ -84,29 +84,29 @@ public class LuaString extends LuaValue { /** The hashcode for this string. Computed at construct time. */ private final int m_hashcode; - /** Size of cache of recent short strings. This is the maximum number of LuaStrings that + /** Size of cache of recent short strings. This is the maximum number of LuaStrings that * will be retained in the cache of recent short strings. Exposed to package for testing. */ static final int RECENT_STRINGS_CACHE_SIZE = 128; - /** Maximum length of a string to be considered for recent short strings caching. + /** Maximum length of a string to be considered for recent short strings caching. * This effectively limits the total memory that can be spent on the recent strings cache, - * because no LuaString whose backing exceeds this length will be put into the cache. + * because no LuaString whose backing exceeds this length will be put into the cache. * Exposed to package for testing. */ static final int RECENT_STRINGS_MAX_LENGTH = 32; - /** Simple cache of recently created strings that are short. - * This is simply a list of strings, indexed by their hash codes modulo the cache size - * that have been recently constructed. If a string is being constructed frequently - * from different contexts, it will generally show up as a cache hit and resolve + /** Simple cache of recently created strings that are short. + * This is simply a list of strings, indexed by their hash codes modulo the cache size + * that have been recently constructed. If a string is being constructed frequently + * from different contexts, it will generally show up as a cache hit and resolve * to the same value. */ private static final class RecentShortStrings { - private static final LuaString recent_short_strings[] = + private static final LuaString recent_short_strings[] = new LuaString[RECENT_STRINGS_CACHE_SIZE]; } /** - * Get a {@link LuaString} instance whose bytes match - * the supplied Java String using the UTF8 encoding. + * Get a {@link LuaString} instance whose bytes match + * the supplied Java String using the UTF8 encoding. * @param string Java String containing characters to encode as UTF8 * @return {@link LuaString} with UTF8 bytes corresponding to the supplied String */ @@ -120,7 +120,7 @@ public class LuaString extends LuaValue { /** Construct a {@link LuaString} for a portion of a byte array. *
* The array is first be used as the backing for this object, so clients must not change contents. - * If the supplied value for 'len' is more than half the length of the container, the + * If the supplied value for 'len' is more than half the length of the container, the * supplied byte array will be used as the backing, otherwise the bytes will be copied to a * new byte array, and cache lookup may be performed. *
@@ -172,11 +172,11 @@ public class LuaString extends LuaValue { /** Construct a {@link LuaString} using the supplied characters as byte values. *
- * Only the low-order 8-bits of each character are used, the remainder is ignored. + * Only the low-order 8-bits of each character are used, the remainder is ignored. *
- * This is most useful for constructing byte sequences that do not conform to UTF8. - * @param bytes array of char, whose values are truncated at 8-bits each and put into a byte array. - * @return {@link LuaString} wrapping a copy of the byte buffer + * This is most useful for constructing byte sequences that do not conform to UTF8. + * @param bytes array of char, whose values are truncated at 8-bits each and put into a byte array. + * @return {@link LuaString} wrapping a copy of the byte buffer */ public static LuaString valueOf(char[] bytes) { return valueOf(bytes, 0, bytes.length); @@ -184,11 +184,11 @@ public class LuaString extends LuaValue { /** Construct a {@link LuaString} using the supplied characters as byte values. *
- * Only the low-order 8-bits of each character are used, the remainder is ignored. + * Only the low-order 8-bits of each character are used, the remainder is ignored. *
- * This is most useful for constructing byte sequences that do not conform to UTF8. - * @param bytes array of char, whose values are truncated at 8-bits each and put into a byte array. - * @return {@link LuaString} wrapping a copy of the byte buffer + * This is most useful for constructing byte sequences that do not conform to UTF8. + * @param bytes array of char, whose values are truncated at 8-bits each and put into a byte array. + * @return {@link LuaString} wrapping a copy of the byte buffer */ public static LuaString valueOf(char[] bytes, int off, int len) { byte[] b = new byte[len]; @@ -215,7 +215,7 @@ public class LuaString extends LuaValue { * The LuaString returned will either be a new LuaString containing the byte array, * or be an existing LuaString used already having the same value. *
- * The caller must not mutate the contents of the byte array after this call, as
+ * The caller must not mutate the contents of the byte array after this call, as
* it may be used elsewhere due to recent short string caching.
* @param bytes byte buffer
* @return {@link LuaString} wrapping the byte buffer
@@ -241,11 +241,11 @@ public class LuaString extends LuaValue {
}
public boolean isstring() {
- return true;
+ return true;
}
- public LuaValue getmetatable() {
- return s_metatable;
+ public LuaValue getmetatable() {
+ return s_metatable;
}
public int type() {
@@ -289,20 +289,20 @@ public class LuaString extends LuaValue {
public LuaValue modFrom( double lhs ) { return LuaDouble.dmod(lhs, checkarith()); }
// relational operators, these only work with other strings
- public LuaValue lt( LuaValue rhs ) { return rhs.strcmp(this)>0? LuaValue.TRUE: FALSE; }
- public boolean lt_b( LuaValue rhs ) { return rhs.strcmp(this)>0; }
+ public LuaValue lt( LuaValue rhs ) { return rhs.isstring() ? (rhs.strcmp(this)>0? LuaValue.TRUE: FALSE) : super.lt(rhs); }
+ public boolean lt_b( LuaValue rhs ) { return rhs.isstring() ? rhs.strcmp(this)>0 : super.lt_b(rhs); }
public boolean lt_b( int rhs ) { typerror("attempt to compare string with number"); return false; }
public boolean lt_b( double rhs ) { typerror("attempt to compare string with number"); return false; }
- public LuaValue lteq( LuaValue rhs ) { return rhs.strcmp(this)>=0? LuaValue.TRUE: FALSE; }
- public boolean lteq_b( LuaValue rhs ) { return rhs.strcmp(this)>=0; }
+ public LuaValue lteq( LuaValue rhs ) { return rhs.isstring() ? (rhs.strcmp(this)>=0? LuaValue.TRUE: FALSE) : super.lteq(rhs); }
+ public boolean lteq_b( LuaValue rhs ) { return rhs.isstring() ? rhs.strcmp(this)>=0 : super.lteq_b(rhs); }
public boolean lteq_b( int rhs ) { typerror("attempt to compare string with number"); return false; }
public boolean lteq_b( double rhs ) { typerror("attempt to compare string with number"); return false; }
- public LuaValue gt( LuaValue rhs ) { return rhs.strcmp(this)<0? LuaValue.TRUE: FALSE; }
- public boolean gt_b( LuaValue rhs ) { return rhs.strcmp(this)<0; }
+ public LuaValue gt( LuaValue rhs ) { return rhs.isstring() ? (rhs.strcmp(this)<0? LuaValue.TRUE: FALSE) : super.gt(rhs); }
+ public boolean gt_b( LuaValue rhs ) { return rhs.isstring() ? rhs.strcmp(this)<0 : super.gt_b(rhs); }
public boolean gt_b( int rhs ) { typerror("attempt to compare string with number"); return false; }
public boolean gt_b( double rhs ) { typerror("attempt to compare string with number"); return false; }
- public LuaValue gteq( LuaValue rhs ) { return rhs.strcmp(this)<=0? LuaValue.TRUE: FALSE; }
- public boolean gteq_b( LuaValue rhs ) { return rhs.strcmp(this)<=0; }
+ public LuaValue gteq( LuaValue rhs ) { return rhs.isstring() ? (rhs.strcmp(this)<=0? LuaValue.TRUE: FALSE) : super.gteq(rhs); }
+ public boolean gteq_b( LuaValue rhs ) { return rhs.isstring() ? rhs.strcmp(this)<=0 : super.gteq_b(rhs); }
public boolean gteq_b( int rhs ) { typerror("attempt to compare string with number"); return false; }
public boolean gteq_b( double rhs ) { typerror("attempt to compare string with number"); return false; }
@@ -310,14 +310,14 @@ public class LuaString extends LuaValue {
public LuaValue concat(LuaValue rhs) { return rhs.concatTo(this); }
public Buffer concat(Buffer rhs) { return rhs.concatTo(this); }
public LuaValue concatTo(LuaNumber lhs) { return concatTo(lhs.strvalue()); }
- public LuaValue concatTo(LuaString lhs) {
+ public LuaValue concatTo(LuaString lhs) {
byte[] b = new byte[lhs.m_length+this.m_length];
System.arraycopy(lhs.m_bytes, lhs.m_offset, b, 0, lhs.m_length);
System.arraycopy(this.m_bytes, this.m_offset, b, lhs.m_length, this.m_length);
return valueUsing(b, 0, b.length);
}
- // string comparison
+ // string comparison
public int strcmp(LuaValue lhs) { return -lhs.strcmp(this); }
public int strcmp(LuaString rhs) {
for ( int i=0, j=0; i
* The string should be measured first with lengthAsUtf8
* to make sure the given byte array is large enough.
@@ -694,11 +694,11 @@ public class LuaString extends LuaValue {
bytes[j++] = (byte) c;
} else if ( c < 0x800 ) {
bytes[j++] = (byte) (0xC0 | ((c>>6) & 0x1f));
- bytes[j++] = (byte) (0x80 | ( c & 0x3f));
+ bytes[j++] = (byte) (0x80 | ( c & 0x3f));
} else {
bytes[j++] = (byte) (0xE0 | ((c>>12) & 0x0f));
bytes[j++] = (byte) (0x80 | ((c>>6) & 0x3f));
- bytes[j++] = (byte) (0x80 | ( c & 0x3f));
+ bytes[j++] = (byte) (0x80 | ( c & 0x3f));
}
}
return j - off;
@@ -714,12 +714,12 @@ public class LuaString extends LuaValue {
for (int i=m_offset,j=m_offset+m_length; i