Add SBT as build system, add Java package annotation for generated code
This commit is contained in:
parent
3175e30cfd
commit
570ff3e2c3
35 changed files with 2649 additions and 0 deletions
6
.gitignore
vendored
Normal file
6
.gitignore
vendored
Normal file
|
@ -0,0 +1,6 @@
|
||||||
|
target/
|
||||||
|
project/target
|
||||||
|
*.iml
|
||||||
|
.idea
|
||||||
|
*.ipr
|
||||||
|
*.iws
|
|
@ -1,3 +1,5 @@
|
||||||
|
package org.capnproto.examples;
|
||||||
|
|
||||||
import org.capnproto.MessageReader;
|
import org.capnproto.MessageReader;
|
||||||
import org.capnproto.StructList;
|
import org.capnproto.StructList;
|
||||||
import org.capnproto.InputStreamMessageReader;
|
import org.capnproto.InputStreamMessageReader;
|
1639
generator/src/main/cpp/compiler/capnpc-java.c++
Normal file
1639
generator/src/main/cpp/compiler/capnpc-java.c++
Normal file
File diff suppressed because it is too large
Load diff
3
generator/src/main/cpp/compiler/java_support/java.capnp
Normal file
3
generator/src/main/cpp/compiler/java_support/java.capnp
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
@0xc5f1af96651f70ea;
|
||||||
|
|
||||||
|
annotation package(file): Text;
|
35
generator/src/main/cpp/compiler/java_support/java.capnp.c++
Normal file
35
generator/src/main/cpp/compiler/java_support/java.capnp.c++
Normal file
|
@ -0,0 +1,35 @@
|
||||||
|
// Generated by Cap'n Proto compiler, DO NOT EDIT
|
||||||
|
// source: java.capnp
|
||||||
|
|
||||||
|
#include "java.capnp.h"
|
||||||
|
|
||||||
|
namespace capnp {
|
||||||
|
namespace schemas {
|
||||||
|
static const ::capnp::_::AlignedData<18> b_9ee4c8f803b3b596 = {
|
||||||
|
{ 0, 0, 0, 0, 5, 0, 5, 0,
|
||||||
|
150, 181, 179, 3, 248, 200, 228, 158,
|
||||||
|
11, 0, 0, 0, 5, 0, 1, 0,
|
||||||
|
234, 112, 31, 101, 150, 175, 241, 197,
|
||||||
|
0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
|
0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
|
17, 0, 0, 0, 154, 0, 0, 0,
|
||||||
|
25, 0, 0, 0, 7, 0, 0, 0,
|
||||||
|
0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
|
20, 0, 0, 0, 2, 0, 1, 0,
|
||||||
|
0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
|
106, 97, 118, 97, 46, 99, 97, 112,
|
||||||
|
110, 112, 58, 112, 97, 99, 107, 97,
|
||||||
|
103, 101, 0, 0, 0, 0, 0, 0,
|
||||||
|
0, 0, 0, 0, 1, 0, 1, 0,
|
||||||
|
12, 0, 0, 0, 0, 0, 0, 0,
|
||||||
|
0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
|
0, 0, 0, 0, 0, 0, 0, 0, }
|
||||||
|
};
|
||||||
|
const ::capnp::_::RawSchema s_9ee4c8f803b3b596 = {
|
||||||
|
0x9ee4c8f803b3b596, b_9ee4c8f803b3b596.words, 18, nullptr, nullptr,
|
||||||
|
0, 0, nullptr, nullptr, nullptr
|
||||||
|
};
|
||||||
|
} // namespace schemas
|
||||||
|
namespace _ { // private
|
||||||
|
} // namespace _ (private)
|
||||||
|
} // namespace capnp
|
36
generator/src/main/cpp/compiler/java_support/java.capnp.h
Normal file
36
generator/src/main/cpp/compiler/java_support/java.capnp.h
Normal file
|
@ -0,0 +1,36 @@
|
||||||
|
// Generated by Cap'n Proto compiler, DO NOT EDIT
|
||||||
|
// source: java.capnp
|
||||||
|
|
||||||
|
#ifndef CAPNP_INCLUDED_c5f1af96651f70ea_
|
||||||
|
#define CAPNP_INCLUDED_c5f1af96651f70ea_
|
||||||
|
|
||||||
|
#include <capnp/generated-header-support.h>
|
||||||
|
|
||||||
|
#if CAPNP_VERSION != 4001
|
||||||
|
#error "Version mismatch between generated code and library headers. You must use the same version of the Cap'n Proto compiler and library."
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
// =======================================================================================
|
||||||
|
|
||||||
|
namespace capnp {
|
||||||
|
namespace schemas {
|
||||||
|
|
||||||
|
extern const ::capnp::_::RawSchema s_9ee4c8f803b3b596;
|
||||||
|
|
||||||
|
} // namespace schemas
|
||||||
|
namespace _ { // private
|
||||||
|
|
||||||
|
|
||||||
|
} // namespace _ (private)
|
||||||
|
} // namespace capnp
|
||||||
|
|
||||||
|
// =======================================================================================
|
||||||
|
|
||||||
|
|
||||||
|
// =======================================================================================
|
||||||
|
|
||||||
|
|
||||||
|
#endif // CAPNP_INCLUDED_c5f1af96651f70ea_
|
17
generator/src/main/java/org/capnproto/AnyPointer.java
Normal file
17
generator/src/main/java/org/capnproto/AnyPointer.java
Normal file
|
@ -0,0 +1,17 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
public class AnyPointer {
|
||||||
|
|
||||||
|
public static class Reader {
|
||||||
|
public PointerReader reader;
|
||||||
|
|
||||||
|
public Reader(PointerReader reader) {
|
||||||
|
this.reader = reader;
|
||||||
|
}
|
||||||
|
|
||||||
|
public <T> T getAsStruct(FromStructReader<T> factory) {
|
||||||
|
return factory.fromStructReader(this.reader.getStruct());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,7 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
public class DecodeException extends RuntimeException {
|
||||||
|
public DecodeException(String message) {
|
||||||
|
super(message);
|
||||||
|
}
|
||||||
|
}
|
12
generator/src/main/java/org/capnproto/FieldSize.java
Normal file
12
generator/src/main/java/org/capnproto/FieldSize.java
Normal file
|
@ -0,0 +1,12 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
public class FieldSize {
|
||||||
|
public static final byte VOID = 0;
|
||||||
|
public static final byte BIT = 1;
|
||||||
|
public static final byte BYTE = 2;
|
||||||
|
public static final byte TWO_BYTES = 3;
|
||||||
|
public static final byte FOUR_BYTES = 4;
|
||||||
|
public static final byte EIGHT_BYTES = 5;
|
||||||
|
public static final byte POINTER = 6;
|
||||||
|
public static final byte INLINE_COMPOSITE = 7;
|
||||||
|
}
|
|
@ -0,0 +1,6 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
public interface FromStructBuilder<T> {
|
||||||
|
public abstract T fromStructBuilder(StructBuilder builder);
|
||||||
|
public abstract StructSize structSize();
|
||||||
|
}
|
|
@ -0,0 +1,5 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
public interface FromStructReader<T> {
|
||||||
|
public abstract T fromStructReader(StructReader reader);
|
||||||
|
}
|
|
@ -0,0 +1,84 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
import java.io.InputStream;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
|
import java.nio.ByteOrder;
|
||||||
|
import java.util.Vector;
|
||||||
|
|
||||||
|
|
||||||
|
public class InputStreamMessageReader {
|
||||||
|
|
||||||
|
static byte[] readExact(InputStream is, int length) throws IOException {
|
||||||
|
byte[] bytes = new byte[length];
|
||||||
|
|
||||||
|
int bytesRead = 0;
|
||||||
|
while (bytesRead < length) {
|
||||||
|
int r = is.read(bytes, bytesRead, length - bytesRead);
|
||||||
|
if (r < 0) {
|
||||||
|
throw new IOException("premature EOF");
|
||||||
|
}
|
||||||
|
bytesRead += r;
|
||||||
|
}
|
||||||
|
|
||||||
|
return bytes;
|
||||||
|
}
|
||||||
|
|
||||||
|
static ByteBuffer makeByteBuffer(byte[] bytes) {
|
||||||
|
ByteBuffer result = ByteBuffer.wrap(bytes);
|
||||||
|
result.order(ByteOrder.LITTLE_ENDIAN);
|
||||||
|
result.mark();
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static MessageReader create(InputStream is) throws IOException {
|
||||||
|
ByteBuffer firstWord = makeByteBuffer(readExact(is, 8));
|
||||||
|
|
||||||
|
int segmentCount = 1 + firstWord.getInt(0);
|
||||||
|
|
||||||
|
int segment0Size = 0;
|
||||||
|
if (segmentCount > 0) {
|
||||||
|
segment0Size = firstWord.getInt(4);
|
||||||
|
}
|
||||||
|
|
||||||
|
int totalWords = segment0Size;
|
||||||
|
|
||||||
|
if (segmentCount > 512) {
|
||||||
|
throw new IOException("too many segments");
|
||||||
|
}
|
||||||
|
|
||||||
|
// in words
|
||||||
|
Vector<Integer> moreSizes = new Vector<Integer>();
|
||||||
|
|
||||||
|
if (segmentCount > 1) {
|
||||||
|
ByteBuffer moreSizesRaw = makeByteBuffer(readExact(is, 4 * (segmentCount & ~1)));
|
||||||
|
for(int ii = 0; ii < segmentCount - 1; ++ii) {
|
||||||
|
int size = moreSizesRaw.getInt(ii * 4);
|
||||||
|
moreSizes.add(size);
|
||||||
|
totalWords += size;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO check that totalWords is reasonable
|
||||||
|
|
||||||
|
byte[] allSegments = readExact(is, totalWords * 8);
|
||||||
|
|
||||||
|
ByteBuffer[] segmentSlices = new ByteBuffer[segmentCount];
|
||||||
|
|
||||||
|
segmentSlices[0] = ByteBuffer.wrap(allSegments, 0, segment0Size * 8);
|
||||||
|
segmentSlices[0].order(ByteOrder.LITTLE_ENDIAN);
|
||||||
|
segmentSlices[0].mark();
|
||||||
|
|
||||||
|
int offset = segment0Size;
|
||||||
|
|
||||||
|
for (int ii = 1; ii < segmentCount; ++ii) {
|
||||||
|
segmentSlices[ii] = ByteBuffer.wrap(allSegments, offset * 8, moreSizes.get(ii - 1) * 8);
|
||||||
|
segmentSlices[ii].order(ByteOrder.LITTLE_ENDIAN);
|
||||||
|
segmentSlices[ii].mark();
|
||||||
|
offset += moreSizes.get(ii - 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
return new MessageReader(segmentSlices);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
24
generator/src/main/java/org/capnproto/ListBuilder.java
Normal file
24
generator/src/main/java/org/capnproto/ListBuilder.java
Normal file
|
@ -0,0 +1,24 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
public final class ListBuilder {
|
||||||
|
SegmentBuilder segment;
|
||||||
|
int ptr; // byte offset to front of list
|
||||||
|
int elementCount;
|
||||||
|
int step; // in bits
|
||||||
|
int structDataSize; // in bits
|
||||||
|
short structPointerCount;
|
||||||
|
|
||||||
|
public ListBuilder(SegmentBuilder segment, int ptr,
|
||||||
|
int elementCount, int step,
|
||||||
|
int structDataSize, short structPointerCount) {
|
||||||
|
this.segment = segment;
|
||||||
|
this.ptr = ptr;
|
||||||
|
this.elementCount = elementCount;
|
||||||
|
this.step = step;
|
||||||
|
this.structDataSize = structDataSize;
|
||||||
|
this.structPointerCount = structPointerCount;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
}
|
17
generator/src/main/java/org/capnproto/ListPointer.java
Normal file
17
generator/src/main/java/org/capnproto/ListPointer.java
Normal file
|
@ -0,0 +1,17 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
|
|
||||||
|
final class ListPointer {
|
||||||
|
public static byte elementSize(int elementSizeAndCount) {
|
||||||
|
return (byte) (elementSizeAndCount & 7);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int elementCount(int elementSizeAndCount) {
|
||||||
|
return elementSizeAndCount >> 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int inlineCompositeWordCount(int elementSizeAndCount) {
|
||||||
|
return elementCount(elementSizeAndCount);
|
||||||
|
}
|
||||||
|
}
|
52
generator/src/main/java/org/capnproto/ListReader.java
Normal file
52
generator/src/main/java/org/capnproto/ListReader.java
Normal file
|
@ -0,0 +1,52 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
public class ListReader {
|
||||||
|
SegmentReader segment;
|
||||||
|
int ptr; // byte offset to front of list
|
||||||
|
int elementCount;
|
||||||
|
int step; // in bits
|
||||||
|
int structDataSize; // in bits
|
||||||
|
short structPointerCount;
|
||||||
|
int nestingLimit;
|
||||||
|
|
||||||
|
|
||||||
|
public ListReader () {
|
||||||
|
this.segment = null;
|
||||||
|
this.ptr = 0;
|
||||||
|
this.elementCount = 0;
|
||||||
|
this.step = 0;
|
||||||
|
this.structDataSize = 0;
|
||||||
|
this.structPointerCount = 0;
|
||||||
|
this.nestingLimit = 0x7fffffff;
|
||||||
|
}
|
||||||
|
|
||||||
|
public ListReader(SegmentReader segment, int ptr,
|
||||||
|
int elementCount, int step,
|
||||||
|
int structDataSize, short structPointerCount,
|
||||||
|
int nestingLimit) {
|
||||||
|
this.segment = segment;
|
||||||
|
this.ptr = ptr;
|
||||||
|
this.elementCount = elementCount;
|
||||||
|
this.step = step;
|
||||||
|
this.structDataSize = structDataSize;
|
||||||
|
this.structPointerCount = structPointerCount;
|
||||||
|
this.nestingLimit = nestingLimit;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
public int size() {
|
||||||
|
return this.elementCount;
|
||||||
|
}
|
||||||
|
|
||||||
|
public StructReader getStructElement(int index) {
|
||||||
|
// TODO check nesting limit
|
||||||
|
|
||||||
|
int indexBit = index * this.step;
|
||||||
|
|
||||||
|
int structData = this.ptr + (indexBit / 8);
|
||||||
|
int structPointers = structData + (this.structDataSize / 8);
|
||||||
|
|
||||||
|
return new StructReader(this.segment, structData, structPointers / 8, this.structDataSize,
|
||||||
|
this.structPointerCount, (byte)(indexBit % 8), this.nestingLimit - 1);
|
||||||
|
}
|
||||||
|
}
|
11
generator/src/main/java/org/capnproto/MessageBuilder.java
Normal file
11
generator/src/main/java/org/capnproto/MessageBuilder.java
Normal file
|
@ -0,0 +1,11 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
public final class MessageBuilder {
|
||||||
|
public <T> T getRoot(FromStructBuilder<T> factory) {
|
||||||
|
throw new Error("unimplemented");
|
||||||
|
}
|
||||||
|
|
||||||
|
public <T> T initRoot(FromStructBuilder<T> factory) {
|
||||||
|
throw new Error("unimplemented");
|
||||||
|
}
|
||||||
|
}
|
20
generator/src/main/java/org/capnproto/MessageReader.java
Normal file
20
generator/src/main/java/org/capnproto/MessageReader.java
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
|
|
||||||
|
public class MessageReader {
|
||||||
|
ByteBuffer[] segmentSlices;
|
||||||
|
|
||||||
|
public MessageReader(ByteBuffer[] segmentSlices) {
|
||||||
|
this.segmentSlices = segmentSlices;
|
||||||
|
}
|
||||||
|
|
||||||
|
public <T> T getRoot(FromStructReader<T> factory) {
|
||||||
|
SegmentReader segment = new SegmentReader(this.segmentSlices[0]);
|
||||||
|
PointerReader pointerReader = PointerReader.getRoot(segment,
|
||||||
|
new WordPointer(this.segmentSlices[0], 0),
|
||||||
|
0x7fffffff /* XXX */);
|
||||||
|
AnyPointer.Reader any = new AnyPointer.Reader(pointerReader);
|
||||||
|
return any.getAsStruct(factory);
|
||||||
|
}
|
||||||
|
}
|
20
generator/src/main/java/org/capnproto/PointerBuilder.java
Normal file
20
generator/src/main/java/org/capnproto/PointerBuilder.java
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
public final class PointerBuilder {
|
||||||
|
public SegmentBuilder segment;
|
||||||
|
public int pointer; // word offset
|
||||||
|
|
||||||
|
public PointerBuilder(SegmentBuilder segment, int pointer) {
|
||||||
|
this.segment = segment;
|
||||||
|
this.pointer = pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
public final ListBuilder initStructList(int elementCount, StructSize elementSize) {
|
||||||
|
return WireHelpers.initStructListPointer(this.pointer, this.segment, elementCount, elementSize);
|
||||||
|
}
|
||||||
|
|
||||||
|
public final void setText(Text.Reader value) {
|
||||||
|
WireHelpers.setTextPointer(this.pointer, this.segment, value);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
49
generator/src/main/java/org/capnproto/PointerReader.java
Normal file
49
generator/src/main/java/org/capnproto/PointerReader.java
Normal file
|
@ -0,0 +1,49 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
public class PointerReader {
|
||||||
|
public SegmentReader segment;
|
||||||
|
public int pointer; // word offset
|
||||||
|
public int nestingLimit;
|
||||||
|
|
||||||
|
public PointerReader() {
|
||||||
|
this.segment = null;
|
||||||
|
this.pointer = 0; // XXX ?
|
||||||
|
this.nestingLimit = 0x7fffffff;
|
||||||
|
}
|
||||||
|
|
||||||
|
public PointerReader(SegmentReader segment, int pointer, int nestingLimit) {
|
||||||
|
this.segment = segment;
|
||||||
|
this.pointer = pointer;
|
||||||
|
this.nestingLimit = nestingLimit;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static PointerReader getRoot(SegmentReader segment,
|
||||||
|
WordPointer location,
|
||||||
|
int nestingLimit) {
|
||||||
|
// TODO bounds check
|
||||||
|
return new PointerReader(segment, location.offset, nestingLimit);
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean isNull() {
|
||||||
|
return this.segment.buffer.getLong(this.pointer) == 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
public StructReader getStruct() {
|
||||||
|
return WireHelpers.readStructPointer(this.segment,
|
||||||
|
this.pointer,
|
||||||
|
this.nestingLimit);
|
||||||
|
}
|
||||||
|
|
||||||
|
public ListReader getList(byte expectedElementSize) {
|
||||||
|
// TODO check nullness
|
||||||
|
return WireHelpers.readListPointer(this.segment,
|
||||||
|
this.pointer,
|
||||||
|
expectedElementSize,
|
||||||
|
this.nestingLimit);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Text.Reader getText() {
|
||||||
|
return WireHelpers.readTextPointer(this.segment,
|
||||||
|
this.pointer);
|
||||||
|
}
|
||||||
|
}
|
34
generator/src/main/java/org/capnproto/SegmentBuilder.java
Normal file
34
generator/src/main/java/org/capnproto/SegmentBuilder.java
Normal file
|
@ -0,0 +1,34 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
|
|
||||||
|
public class SegmentBuilder extends SegmentReader {
|
||||||
|
public int pos = 0; // in words
|
||||||
|
|
||||||
|
public static final int FAILED_ALLOCATION = -1;
|
||||||
|
|
||||||
|
public SegmentBuilder(ByteBuffer buf) {
|
||||||
|
super(buf);
|
||||||
|
}
|
||||||
|
|
||||||
|
// the total number of words the buffer can hold
|
||||||
|
private final int capacity() {
|
||||||
|
this.buffer.reset();
|
||||||
|
return this.buffer.remaining() / 8;
|
||||||
|
}
|
||||||
|
|
||||||
|
// return how many words have already been allocated
|
||||||
|
private final int currentSize() {
|
||||||
|
return this.pos;
|
||||||
|
}
|
||||||
|
|
||||||
|
public final int allocate(int amount) {
|
||||||
|
if (amount > this.capacity() - this.currentSize()) {
|
||||||
|
return FAILED_ALLOCATION; // no space left;
|
||||||
|
} else {
|
||||||
|
int result = this.pos;
|
||||||
|
this.pos += amount;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
11
generator/src/main/java/org/capnproto/SegmentReader.java
Normal file
11
generator/src/main/java/org/capnproto/SegmentReader.java
Normal file
|
@ -0,0 +1,11 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
|
|
||||||
|
public class SegmentReader {
|
||||||
|
ByteBuffer buffer;
|
||||||
|
|
||||||
|
public SegmentReader(ByteBuffer buffer) {
|
||||||
|
this.buffer = buffer;
|
||||||
|
}
|
||||||
|
}
|
42
generator/src/main/java/org/capnproto/StructBuilder.java
Normal file
42
generator/src/main/java/org/capnproto/StructBuilder.java
Normal file
|
@ -0,0 +1,42 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
public final class StructBuilder {
|
||||||
|
public SegmentBuilder segment;
|
||||||
|
public int data; //byte offset to data section
|
||||||
|
public int pointers; // word offset of pointer section
|
||||||
|
public int dataSize; // in bits
|
||||||
|
public short pointerCount;
|
||||||
|
public byte bit0Offset;
|
||||||
|
|
||||||
|
public StructBuilder(SegmentBuilder segment, int data,
|
||||||
|
int pointers, int dataSize, short pointerCount,
|
||||||
|
byte bit0Offset) {
|
||||||
|
this.segment = segment;
|
||||||
|
this.data = data;
|
||||||
|
this.pointers = pointers;
|
||||||
|
this.dataSize = dataSize;
|
||||||
|
this.pointerCount = pointerCount;
|
||||||
|
this.bit0Offset = bit0Offset;
|
||||||
|
}
|
||||||
|
|
||||||
|
public final int getShortField(int offset) {
|
||||||
|
return this.segment.buffer.getShort(this.data + offset * 2);
|
||||||
|
}
|
||||||
|
|
||||||
|
public final void setShortField(int offset, short value) {
|
||||||
|
this.segment.buffer.putShort(this.data + offset * 2, value);
|
||||||
|
}
|
||||||
|
|
||||||
|
public final int getIntField(int offset) {
|
||||||
|
return this.segment.buffer.getInt(this.data + offset * 4);
|
||||||
|
}
|
||||||
|
|
||||||
|
public final void setIntField(int offset, int value) {
|
||||||
|
this.segment.buffer.putInt(this.data + offset * 4, value);
|
||||||
|
}
|
||||||
|
|
||||||
|
public final PointerBuilder getPointerField(int index) {
|
||||||
|
return new PointerBuilder(this.segment, this.pointers + index);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
34
generator/src/main/java/org/capnproto/StructList.java
Normal file
34
generator/src/main/java/org/capnproto/StructList.java
Normal file
|
@ -0,0 +1,34 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
|
||||||
|
public final class StructList {
|
||||||
|
public static final class Reader<T> {
|
||||||
|
public ListReader reader;
|
||||||
|
public final FromStructReader<T> factory;
|
||||||
|
|
||||||
|
public Reader(ListReader reader, FromStructReader<T> factory) {
|
||||||
|
this.reader = reader;
|
||||||
|
this.factory = factory;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int size() {
|
||||||
|
return this.reader.size();
|
||||||
|
}
|
||||||
|
|
||||||
|
public T get(int index) {
|
||||||
|
return this.factory.fromStructReader(this.reader.getStructElement(index));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static final class Builder<T> {
|
||||||
|
public ListBuilder builder;
|
||||||
|
public final FromStructBuilder<T> factory;
|
||||||
|
|
||||||
|
public Builder(ListBuilder builder, FromStructBuilder<T> factory) {
|
||||||
|
this.builder = builder;
|
||||||
|
this.factory = factory;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
17
generator/src/main/java/org/capnproto/StructPointer.java
Normal file
17
generator/src/main/java/org/capnproto/StructPointer.java
Normal file
|
@ -0,0 +1,17 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
|
|
||||||
|
final class StructPointer{
|
||||||
|
public static short dataSize(int structRef) {
|
||||||
|
return (short)(structRef & 0xffff);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static short ptrCount(int structRef) {
|
||||||
|
return (short)(structRef >> 16);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int wordSize(int structRef) {
|
||||||
|
return (int)dataSize(structRef) + (int)ptrCount(structRef);
|
||||||
|
}
|
||||||
|
}
|
71
generator/src/main/java/org/capnproto/StructReader.java
Normal file
71
generator/src/main/java/org/capnproto/StructReader.java
Normal file
|
@ -0,0 +1,71 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
public final class StructReader {
|
||||||
|
public SegmentReader segment;
|
||||||
|
public int data; //byte offset to data section
|
||||||
|
public int pointers; // word offset of pointer section
|
||||||
|
public int dataSize; // in bits
|
||||||
|
public short pointerCount;
|
||||||
|
public byte bit0Offset;
|
||||||
|
public int nestingLimit;
|
||||||
|
|
||||||
|
|
||||||
|
public StructReader(SegmentReader segment, int data,
|
||||||
|
int pointers, int dataSize, short pointerCount,
|
||||||
|
byte bit0Offset, int nestingLimit) {
|
||||||
|
this.segment = segment;
|
||||||
|
this.data = data;
|
||||||
|
this.pointers = pointers;
|
||||||
|
this.dataSize = dataSize;
|
||||||
|
this.pointerCount = pointerCount;
|
||||||
|
this.bit0Offset = bit0Offset;
|
||||||
|
this.nestingLimit = nestingLimit;
|
||||||
|
}
|
||||||
|
|
||||||
|
public final boolean getBoolField(int offset) {
|
||||||
|
// XXX should use unsigned operations
|
||||||
|
if (offset < this.dataSize) {
|
||||||
|
if (offset == 0) {
|
||||||
|
offset = this.bit0Offset;
|
||||||
|
}
|
||||||
|
byte b = this.segment.buffer.get(offset / 8);
|
||||||
|
return (b & (1 << (offset % 8))) != 0;
|
||||||
|
} else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public final byte getByteField(int offset) {
|
||||||
|
if ((offset + 1) * 8 <= this.dataSize) {
|
||||||
|
return this.segment.buffer.get(this.data + offset);
|
||||||
|
} else {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public final byte getShortField(int offset) {
|
||||||
|
if ((offset + 1) * 16 <= this.dataSize) {
|
||||||
|
return this.segment.buffer.get(this.data + offset * 2);
|
||||||
|
} else {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public final int getIntField(int offset) {
|
||||||
|
if ((offset + 1) * 32 <= this.dataSize) {
|
||||||
|
return this.segment.buffer.getInt(this.data + offset * 4);
|
||||||
|
} else {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public final PointerReader getPointerField(int ptrIndex) {
|
||||||
|
if (ptrIndex < this.pointerCount) {
|
||||||
|
return new PointerReader(this.segment,
|
||||||
|
this.pointers + ptrIndex,
|
||||||
|
this.nestingLimit);
|
||||||
|
} else {
|
||||||
|
return new PointerReader();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
18
generator/src/main/java/org/capnproto/StructSize.java
Normal file
18
generator/src/main/java/org/capnproto/StructSize.java
Normal file
|
@ -0,0 +1,18 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
public final class StructSize {
|
||||||
|
public final short data; // number of words in data section
|
||||||
|
public final short pointers; // number of words in pointer section
|
||||||
|
public final byte preferredListEncoding; // a FieldSize
|
||||||
|
|
||||||
|
public StructSize(short data, short pointers, byte preferredListEncoding) {
|
||||||
|
this.data = data;
|
||||||
|
this.pointers = pointers;
|
||||||
|
this.preferredListEncoding = preferredListEncoding;
|
||||||
|
}
|
||||||
|
|
||||||
|
public final int total() {
|
||||||
|
return (int)this.data + (int)this.pointers;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
45
generator/src/main/java/org/capnproto/Text.java
Normal file
45
generator/src/main/java/org/capnproto/Text.java
Normal file
|
@ -0,0 +1,45 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
|
|
||||||
|
public class Text {
|
||||||
|
|
||||||
|
public static class Reader {
|
||||||
|
public final ByteBuffer buffer;
|
||||||
|
public final int offset; // in bytes
|
||||||
|
public final int size; // in bytes
|
||||||
|
|
||||||
|
public Reader(ByteBuffer buffer, int offset, int size) {
|
||||||
|
this.buffer = buffer;
|
||||||
|
this.offset = offset * 8;
|
||||||
|
this.size = size;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Reader(String value) {
|
||||||
|
try {
|
||||||
|
byte[] bytes = value.getBytes("UTF-8");
|
||||||
|
this.buffer = ByteBuffer.wrap(bytes);
|
||||||
|
this.offset = 0;
|
||||||
|
this.size = bytes.length;
|
||||||
|
} catch (java.io.UnsupportedEncodingException e) {
|
||||||
|
throw new Error("UTF-8 is unsupported");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public final String toString() {
|
||||||
|
byte[] bytes = new byte[this.size];
|
||||||
|
|
||||||
|
this.buffer.position(this.offset);
|
||||||
|
this.buffer.get(bytes, 0, this.size);
|
||||||
|
|
||||||
|
try {
|
||||||
|
return new String(bytes, "UTF-8");
|
||||||
|
} catch(java.io.UnsupportedEncodingException e) {
|
||||||
|
return "unsupported encoding"; // XXX
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
174
generator/src/main/java/org/capnproto/WireHelpers.java
Normal file
174
generator/src/main/java/org/capnproto/WireHelpers.java
Normal file
|
@ -0,0 +1,174 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
final class WireHelpers {
|
||||||
|
|
||||||
|
public static int roundBytesUpToWords(int bytes) {
|
||||||
|
return (bytes + 7) / 8;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int allocate(int refOffset,
|
||||||
|
SegmentBuilder segment,
|
||||||
|
int amount,
|
||||||
|
byte kind) {
|
||||||
|
|
||||||
|
// TODO check for nullness, amount == 0 case.
|
||||||
|
|
||||||
|
int allocation = segment.allocate(amount);
|
||||||
|
if (allocation == SegmentBuilder.FAILED_ALLOCATION) {
|
||||||
|
//# Need to allocate in a new segment. We'll need to
|
||||||
|
//# allocate an extra pointer worth of space to act as
|
||||||
|
//# the landing pad for a far pointer.
|
||||||
|
throw new Error("unimplemented");
|
||||||
|
} else {
|
||||||
|
WirePointer.setKindAndTarget(segment.buffer, refOffset, kind, allocation);
|
||||||
|
return allocation;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static ListBuilder initListPointer(int refOffset,
|
||||||
|
SegmentBuilder segment,
|
||||||
|
int elementCount,
|
||||||
|
byte elementSize) {
|
||||||
|
throw new Error("unimplemented");
|
||||||
|
}
|
||||||
|
|
||||||
|
public static ListBuilder initStructListPointer(int refOffset,
|
||||||
|
SegmentBuilder segment,
|
||||||
|
int elementCount,
|
||||||
|
StructSize elementSize) {
|
||||||
|
if (elementSize.preferredListEncoding != FieldSize.INLINE_COMPOSITE) {
|
||||||
|
//# Small data-only struct. Allocate a list of primitives instead.
|
||||||
|
return initListPointer(refOffset, segment, elementCount,
|
||||||
|
elementSize.preferredListEncoding);
|
||||||
|
}
|
||||||
|
|
||||||
|
int wordsPerElement = elementSize.total();
|
||||||
|
|
||||||
|
throw new Error("unimplemented");
|
||||||
|
}
|
||||||
|
|
||||||
|
// size is in bytes
|
||||||
|
public static void initTextPointer(int refOffset,
|
||||||
|
SegmentBuilder segment,
|
||||||
|
int size) {
|
||||||
|
//# The byte list must include a NUL terminator.
|
||||||
|
int byteSize = size + 1;
|
||||||
|
|
||||||
|
int ptrOffset = allocate(refOffset, segment, roundBytesUpToWords(byteSize), WirePointer.LIST);
|
||||||
|
|
||||||
|
throw new Error("unimplemented");
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void setTextPointer(int refOffset,
|
||||||
|
SegmentBuilder segment,
|
||||||
|
Text.Reader value) {
|
||||||
|
throw new Error("unimplemented");
|
||||||
|
}
|
||||||
|
|
||||||
|
public static StructReader readStructPointer(SegmentReader segment,
|
||||||
|
int refOffset,
|
||||||
|
int nestingLimit) {
|
||||||
|
|
||||||
|
// TODO error handling
|
||||||
|
|
||||||
|
if (nestingLimit < 0) {
|
||||||
|
throw new DecodeException("Message is too deeply nested or contains cycles.");
|
||||||
|
}
|
||||||
|
|
||||||
|
long ref = WirePointer.get(segment.buffer, refOffset);
|
||||||
|
int ptrOffset = WirePointer.target(refOffset, ref);
|
||||||
|
int structPtr = WirePointer.structPointer(ref);
|
||||||
|
int dataSizeWords = StructPointer.dataSize(structPtr);
|
||||||
|
|
||||||
|
return new StructReader(segment,
|
||||||
|
ptrOffset * 8,
|
||||||
|
(ptrOffset + dataSizeWords),
|
||||||
|
dataSizeWords * 64,
|
||||||
|
StructPointer.ptrCount(structPtr),
|
||||||
|
(byte)0,
|
||||||
|
nestingLimit - 1);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
public static ListReader readListPointer(SegmentReader segment,
|
||||||
|
int refOffset,
|
||||||
|
byte expectedElementSize,
|
||||||
|
int nestingLimit) {
|
||||||
|
|
||||||
|
long ref = WirePointer.get(segment.buffer, refOffset);
|
||||||
|
|
||||||
|
// TODO check for null, follow fars, nestingLimit
|
||||||
|
if (WirePointer.isNull(ref)) {
|
||||||
|
return new ListReader();
|
||||||
|
}
|
||||||
|
|
||||||
|
int listPtr = WirePointer.listPointer(ref);
|
||||||
|
|
||||||
|
int ptrOffset = WirePointer.target(refOffset, ref);
|
||||||
|
long ptr = WirePointer.get(segment.buffer, ptrOffset);
|
||||||
|
|
||||||
|
switch (ListPointer.elementSize(listPtr)) {
|
||||||
|
case FieldSize.INLINE_COMPOSITE : {
|
||||||
|
int wordCount = ListPointer.inlineCompositeWordCount(listPtr);
|
||||||
|
|
||||||
|
long tag = ptr;
|
||||||
|
ptrOffset += 1;
|
||||||
|
|
||||||
|
// TODO bounds check
|
||||||
|
|
||||||
|
int size = WirePointer.inlineCompositeListElementCount(tag);
|
||||||
|
|
||||||
|
int structPtr = WirePointer.structPointer(tag);
|
||||||
|
int wordsPerElement = StructPointer.wordSize(structPtr);
|
||||||
|
|
||||||
|
// TODO check that elemements do not overrun word count
|
||||||
|
|
||||||
|
// TODO check whether the size is compatible
|
||||||
|
|
||||||
|
return new ListReader(segment, // TODO follow fars
|
||||||
|
ptrOffset * 8, //
|
||||||
|
size,
|
||||||
|
wordsPerElement * 64,
|
||||||
|
StructPointer.dataSize(structPtr) * 64,
|
||||||
|
StructPointer.ptrCount(structPtr),
|
||||||
|
nestingLimit - 1);
|
||||||
|
}
|
||||||
|
case FieldSize.VOID : break;
|
||||||
|
default :
|
||||||
|
throw new Error("unrecognized element size");
|
||||||
|
}
|
||||||
|
|
||||||
|
throw new Error();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Text.Reader readTextPointer(SegmentReader segment,
|
||||||
|
int refOffset) {
|
||||||
|
long ref = WirePointer.get(segment.buffer, refOffset);
|
||||||
|
|
||||||
|
if (WirePointer.isNull(ref)) {
|
||||||
|
// XXX should use the default value
|
||||||
|
return new Text.Reader(java.nio.ByteBuffer.wrap(new byte[0]), 0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
int ptrOffset = WirePointer.target(refOffset, ref);
|
||||||
|
int listPtr = WirePointer.listPointer(ref);
|
||||||
|
int size = ListPointer.elementCount(listPtr);
|
||||||
|
|
||||||
|
if (WirePointer.kind(ref) != WirePointer.LIST) {
|
||||||
|
throw new DecodeException("Message contains non-list pointer where text was expected.");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ListPointer.elementSize(listPtr) != FieldSize.BYTE) {
|
||||||
|
throw new DecodeException("Message contains list pointer of non-bytes where text was expected.");
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO bounds check?
|
||||||
|
|
||||||
|
if (size == 0 || segment.buffer.get(8 * ptrOffset + size - 1) != 0) {
|
||||||
|
throw new DecodeException("Message contains text that is not NUL-terminated.");
|
||||||
|
}
|
||||||
|
|
||||||
|
return new Text.Reader(segment.buffer, ptrOffset, size - 1);
|
||||||
|
}
|
||||||
|
}
|
51
generator/src/main/java/org/capnproto/WirePointer.java
Normal file
51
generator/src/main/java/org/capnproto/WirePointer.java
Normal file
|
@ -0,0 +1,51 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
|
|
||||||
|
final class WirePointer {
|
||||||
|
public static final byte STRUCT = 0;
|
||||||
|
public static final byte LIST = 1;
|
||||||
|
public static final byte FAR = 2;
|
||||||
|
public static final byte OTHER = 3;
|
||||||
|
|
||||||
|
public static boolean isNull(long wirePointer) {
|
||||||
|
return wirePointer == 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int offsetAndKind(long wirePointer) {
|
||||||
|
return (int)(wirePointer & 0xffffffff);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static byte kind(long wirePointer) {
|
||||||
|
return (byte)(offsetAndKind(wirePointer) & 3);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int target(int offset, long wirePointer) {
|
||||||
|
return offset + 1 + (offsetAndKind(wirePointer) >> 2);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void setKindAndTarget(ByteBuffer buffer, int offset, byte kind, int targetOffset) {
|
||||||
|
buffer.putInt(offset * 8,
|
||||||
|
(((targetOffset - offset) - 1) << 2) | kind);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int inlineCompositeListElementCount(long wirePointer) {
|
||||||
|
return offsetAndKind(wirePointer) >> 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int upper32Bits(long wirePointer) {
|
||||||
|
return (int)(wirePointer >> 32);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int listPointer(long wirePointer) {
|
||||||
|
return upper32Bits(wirePointer);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int structPointer(long wirePointer) {
|
||||||
|
return upper32Bits(wirePointer);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static long get(ByteBuffer buffer, int offset) {
|
||||||
|
return buffer.getLong(offset * 8);
|
||||||
|
}
|
||||||
|
}
|
13
generator/src/main/java/org/capnproto/WordPointer.java
Normal file
13
generator/src/main/java/org/capnproto/WordPointer.java
Normal file
|
@ -0,0 +1,13 @@
|
||||||
|
package org.capnproto;
|
||||||
|
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
|
|
||||||
|
class WordPointer {
|
||||||
|
public final ByteBuffer buffer;
|
||||||
|
public int offset; // in words
|
||||||
|
|
||||||
|
public WordPointer(ByteBuffer buffer, int offset) {
|
||||||
|
this.buffer = buffer;
|
||||||
|
this.offset = offset;
|
||||||
|
}
|
||||||
|
}
|
1
project/build.properties
Normal file
1
project/build.properties
Normal file
|
@ -0,0 +1 @@
|
||||||
|
sbt.version=0.13.2
|
89
project/build.scala
Normal file
89
project/build.scala
Normal file
|
@ -0,0 +1,89 @@
|
||||||
|
import sbt.Keys._
|
||||||
|
import sbt._
|
||||||
|
|
||||||
|
object Build extends sbt.Build {
|
||||||
|
|
||||||
|
lazy val root =
|
||||||
|
project(
|
||||||
|
id = "capnproto-java",
|
||||||
|
base = file(".")
|
||||||
|
).aggregate(generator, examples)
|
||||||
|
|
||||||
|
lazy val generator =
|
||||||
|
project(
|
||||||
|
id = "generator",
|
||||||
|
base = file("generator")
|
||||||
|
).settings(Defaults.itSettings: _*)
|
||||||
|
.settings(compile <<= compile in Compile dependsOn(compile in Test, compile in IntegrationTest))
|
||||||
|
|
||||||
|
lazy val examples =
|
||||||
|
project(
|
||||||
|
id = "examples",
|
||||||
|
base = file("examples")
|
||||||
|
).dependsOn(generator)
|
||||||
|
.settings(publish := {})
|
||||||
|
.settings(publishLocal := {})
|
||||||
|
.settings(fork in run := true)
|
||||||
|
.settings(outputStrategy := Some(StdoutOutput))
|
||||||
|
.settings(javaOptions in run ++= Seq(
|
||||||
|
"-ms2g",
|
||||||
|
"-mx2g",
|
||||||
|
"-XX:+AlwaysPreTouch",
|
||||||
|
"-XX:+TieredCompilation"
|
||||||
|
))
|
||||||
|
|
||||||
|
def project(id: String, base: File) =
|
||||||
|
Project(
|
||||||
|
id = id,
|
||||||
|
base = base,
|
||||||
|
settings =
|
||||||
|
Project.defaultSettings ++
|
||||||
|
Shared.settings ++
|
||||||
|
Seq(libraryDependencies ++= Shared.testDeps)
|
||||||
|
).configs(IntegrationTest)
|
||||||
|
}
|
||||||
|
|
||||||
|
object Shared {
|
||||||
|
|
||||||
|
val testDeps = Seq(
|
||||||
|
"org.scalatest" %% "scalatest" % "2.1.6" % "it,test",
|
||||||
|
"org.scalacheck" %% "scalacheck" % "1.11.4" % "it,test"
|
||||||
|
)
|
||||||
|
|
||||||
|
val settings = Seq(
|
||||||
|
scalaVersion := "2.11.0",
|
||||||
|
scalacOptions := Seq(
|
||||||
|
"-deprecation",
|
||||||
|
"-feature",
|
||||||
|
"-optimise",
|
||||||
|
"-Yinline-warnings",
|
||||||
|
"-unchecked",
|
||||||
|
"-feature"
|
||||||
|
),
|
||||||
|
resolvers += Resolver.sonatypeRepo("snapshots"),
|
||||||
|
resolvers += Resolver.sonatypeRepo("releases"),
|
||||||
|
shellPrompt := ShellPrompt.buildShellPrompt
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
object ShellPrompt {
|
||||||
|
object devnull extends ProcessLogger {
|
||||||
|
def info(s: => String) {}
|
||||||
|
def error(s: => String) {}
|
||||||
|
def buffer[T](f: => T): T = f
|
||||||
|
}
|
||||||
|
|
||||||
|
def currBranch = (
|
||||||
|
("git status -sb" lines_! devnull headOption)
|
||||||
|
getOrElse "-" stripPrefix "## "
|
||||||
|
)
|
||||||
|
|
||||||
|
val buildShellPrompt = {
|
||||||
|
(state: State) => {
|
||||||
|
val currProject = Project.extract(state).currentProject.id
|
||||||
|
"[%s](%s)$ ".format(
|
||||||
|
currProject, currBranch /*, BuildSettings.buildVersion*/
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
3
project/plugins.sbt
Normal file
3
project/plugins.sbt
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
addSbtPlugin("com.github.mpeltonen" % "sbt-idea" % "1.5.2")
|
||||||
|
|
||||||
|
addSbtPlugin("net.virtual-void" % "sbt-dependency-graph" % "0.7.4")
|
1
version.sbt
Normal file
1
version.sbt
Normal file
|
@ -0,0 +1 @@
|
||||||
|
version in ThisBuild := "0.1.0"
|
Loading…
Reference in a new issue