자바에서 unsigned 타입을 사용하는 프로토콜을 처리하기 위한 클래스들..

자바(Java)를 사용해서 개발한 서비스나 애플리케이션에서 C/C++로 개발된 서버에 연결해서 데이터를 전송하거나 수신하는 경우에 unsigned로 인해서 통신에 불편함이 발생하게 된다. 그래서 이런 문제를 쉽게 해결하기 위해서 구글에서는 프로토콜 버퍼(https://developers.google.com/protocol-buffers/), 스리프트(페이스북에서 개발해서 아파치에 기증, https://thrift.apache.org/)와 같은 직렬화 라이브러리를 많이 사용하고 있다.
그래도 이런 직렬화 라이브러리를 사용하지 않고, unsigned 타입을 프로토콜로 사용하는 서버와 통신하기 위해서 unsigned를 처리하는 자바 클래스 몇 개를 살펴보자. 아래 클래스는 1, 2, 4 byte의 배열을 읽어서 2, 4, 8 byte의 데이터 타입으로 사용하고, 2, 4, 8 byte를  unsigned 1, 2, 4 byte로 변경하는 코드이다.

1. UnsignedByte

public class UnsignedByte {

    public static short parse( byte[] data, int offset ) {
        return (short)(data[offset] & 0xff);
    }

    public static short parse( byte[] data ) {
        return parse( data, 0 );
    }

    public static byte[] parse( short number ) {
        return new byte[] { (byte)(number & 0xff) };
    }

}

2. UnsignedShort

public class UnsignedShort {

    public static int parse( byte[] data ) {
        return parse( data, 0 );
    }

    public static int parse( byte[] data, int offset ) {
        return ((data[offset] & 0xff) << 8) | (data[offset+1] & 0xff);
    }

    public static byte[] parse( int number ) {
        byte[] data = new byte[2];

        data[0] = (byte)((number >> 8) & 0xff);
        data[1] = (byte)(number & 0xff);

        return data;
    }

}

3. UnsignedInt

public class UnsignedInt {

    public static long parse( byte[] data ) {
        return parse( data, 0 );
    }

    public static long parse( byte[] data, int offset ) {
        return (((long) data[offset] & 0xffL) << 24)
             | (((long) data[offset+1] & 0xffL) << 16)
             | (((long) data[offset+2] & 0xffL) << 8)
             |  ((long) data[offset+3] & 0xffL);
    }

    public static byte[] parse( long number ) {
        byte[] data = new byte[4];
        
        data[0] = (byte) ((number >> 24) & 0xff);
        data[1] = (byte) ((number >> 16) & 0xff);
        data[2] = (byte) ((number >> 8) & 0xff);
        data[3] = (byte) (number & 0xff);

        return data;
    }

}

* Reference
https://github.com/ryantenney/oscar

답글 남기기

이메일은 공개되지 않습니다. 필수 입력창은 * 로 표시되어 있습니다.