diff options
Diffstat (limited to 'lib/src/main/kotlin/QID.kt')
-rw-r--r-- | lib/src/main/kotlin/QID.kt | 105 |
1 files changed, 105 insertions, 0 deletions
diff --git a/lib/src/main/kotlin/QID.kt b/lib/src/main/kotlin/QID.kt new file mode 100644 index 0000000..4d0bd6a --- /dev/null +++ b/lib/src/main/kotlin/QID.kt @@ -0,0 +1,105 @@ +import net.InMessage +import net.OutMessage +import java.math.BigInteger + +/** + * This class holds information about a single QID. + */ +class QID { + /** + * Does the QID represent a directory? + */ + val isDirectory get() = getIsDirectory() + + /** + * Does the QID represent an append-only file? + */ + val isAppendOnly get() = getIsAppendOnly() + + /** + * Does the QID represent an exclusive-use file? + */ + val isExclusive get() = getIsExclusive() + + /** + * Does the QID represent a temporary file? + */ + val isTemporary get() = getIsTemporary() + + /** + * The QID type. + */ + val type: UByte + + /** + * The QID file version. + */ + val version: UInt + + /** + * The QID path. + */ + val path: ULong + + /** + * Constructor for a QID with separate fields. See the `stat(5)` manual page for more information about [type], + * [version], and [path]. + * + * @param type The QID type. + * @param version The QID file version. + * @param path The QID path. + */ + constructor(type: UByte, version: UInt, path: ULong) { + this.type = type + this.version = version + this.path = path + } + + /** + * Constructor for raw QID data. Only the first 13 elements are read. + * + * @param raw The raw QID data. + * @throws IllegalArgumentException if [raw] does not have at least 13 elements. + */ + constructor(raw: List<UByte>) { + require(raw.size >= 13) + this.type = raw.first() + val rawVersion = raw.slice(1..4) + val rawPath = raw.slice(5..12) + this.version = InMessage.convInteger(rawVersion, 0, rawVersion.size).toInt().toUInt() + this.path = InMessage.convInteger(rawPath, 0, rawPath.size).toLong().toULong() + } + + /** + * Check bit values in [type]. In case of multiple bits, the method returns true if at least one of them is 1. + * + * @param bits A byte whose bits set to 1 are checked. + */ + private fun checkTypeBits(bits: UByte): Boolean { + return this.type.and(bits) != 0u.toUByte() + } + + private fun getIsDirectory(): Boolean { + return checkTypeBits(0x80u) + } + + private fun getIsAppendOnly(): Boolean { + return checkTypeBits(0x40u) + } + + private fun getIsExclusive(): Boolean { + return checkTypeBits(0x20u) + } + + private fun getIsTemporary(): Boolean { + return checkTypeBits(0x04u) + } + + fun toRaw(): List<UByte> { + var bytes: List<UByte> = emptyList() + bytes += this.type + bytes += OutMessage.convIntegerToBytes(BigInteger(this.version.toString()), 4u) + bytes += OutMessage.convIntegerToBytes(BigInteger(this.path.toString()), 8u) + return bytes + } +}
\ No newline at end of file |