Update (#680)

 * fix MSVC warnings
 * cleanups
diff --git a/c/common/platform.h b/c/common/platform.h
index b1fb996..3fd0305 100755
--- a/c/common/platform.h
+++ b/c/common/platform.h
@@ -628,7 +628,8 @@
 #define BROTLI_DUMP() (void)(0)
 #endif
 
-#if (BROTLI_MODERN_COMPILER || defined(__llvm__)) && \
+/* TODO: add appropriate icc/sunpro/arm/ibm/ti checks. */
+#if (BROTLI_GNUC_VERSION_CHECK(3, 0, 0) || defined(__llvm__)) && \
     !defined(BROTLI_BUILD_NO_RBIT)
 #if defined(BROTLI_TARGET_ARMV7) || defined(BROTLI_TARGET_ARMV8)
 /* TODO: detect ARMv6T2 and enable this code for it. */
@@ -680,32 +681,32 @@
 }
 
 BROTLI_UNUSED_FUNCTION void BrotliSuppressUnusedFunctions(void) {
-  BROTLI_UNUSED(BrotliSuppressUnusedFunctions);
-  BROTLI_UNUSED(BrotliUnalignedRead16);
-  BROTLI_UNUSED(BrotliUnalignedRead32);
-  BROTLI_UNUSED(BrotliUnalignedRead64);
-  BROTLI_UNUSED(BrotliUnalignedWrite64);
-  BROTLI_UNUSED(BROTLI_UNALIGNED_LOAD16LE);
-  BROTLI_UNUSED(BROTLI_UNALIGNED_LOAD32LE);
-  BROTLI_UNUSED(BROTLI_UNALIGNED_LOAD64LE);
-  BROTLI_UNUSED(BROTLI_UNALIGNED_STORE64LE);
-  BROTLI_UNUSED(BrotliRBit);
-  BROTLI_UNUSED(brotli_min_double);
-  BROTLI_UNUSED(brotli_max_double);
-  BROTLI_UNUSED(brotli_min_float);
-  BROTLI_UNUSED(brotli_max_float);
-  BROTLI_UNUSED(brotli_min_int);
-  BROTLI_UNUSED(brotli_max_int);
-  BROTLI_UNUSED(brotli_min_size_t);
-  BROTLI_UNUSED(brotli_max_size_t);
-  BROTLI_UNUSED(brotli_min_uint32_t);
-  BROTLI_UNUSED(brotli_max_uint32_t);
-  BROTLI_UNUSED(brotli_min_uint8_t);
-  BROTLI_UNUSED(brotli_max_uint8_t);
-  BROTLI_UNUSED(BrotliDefaultAllocFunc);
-  BROTLI_UNUSED(BrotliDefaultFreeFunc);
+  BROTLI_UNUSED(&BrotliSuppressUnusedFunctions);
+  BROTLI_UNUSED(&BrotliUnalignedRead16);
+  BROTLI_UNUSED(&BrotliUnalignedRead32);
+  BROTLI_UNUSED(&BrotliUnalignedRead64);
+  BROTLI_UNUSED(&BrotliUnalignedWrite64);
+  BROTLI_UNUSED(&BROTLI_UNALIGNED_LOAD16LE);
+  BROTLI_UNUSED(&BROTLI_UNALIGNED_LOAD32LE);
+  BROTLI_UNUSED(&BROTLI_UNALIGNED_LOAD64LE);
+  BROTLI_UNUSED(&BROTLI_UNALIGNED_STORE64LE);
+  BROTLI_UNUSED(&BrotliRBit);
+  BROTLI_UNUSED(&brotli_min_double);
+  BROTLI_UNUSED(&brotli_max_double);
+  BROTLI_UNUSED(&brotli_min_float);
+  BROTLI_UNUSED(&brotli_max_float);
+  BROTLI_UNUSED(&brotli_min_int);
+  BROTLI_UNUSED(&brotli_max_int);
+  BROTLI_UNUSED(&brotli_min_size_t);
+  BROTLI_UNUSED(&brotli_max_size_t);
+  BROTLI_UNUSED(&brotli_min_uint32_t);
+  BROTLI_UNUSED(&brotli_max_uint32_t);
+  BROTLI_UNUSED(&brotli_min_uint8_t);
+  BROTLI_UNUSED(&brotli_max_uint8_t);
+  BROTLI_UNUSED(&BrotliDefaultAllocFunc);
+  BROTLI_UNUSED(&BrotliDefaultFreeFunc);
 #if defined(BROTLI_DEBUG) || defined(BROTLI_ENABLE_LOG)
-  BROTLI_UNUSED(BrotliDump);
+  BROTLI_UNUSED(&BrotliDump);
 #endif
 }
 
diff --git a/c/enc/encode.c b/c/enc/encode.c
index 7b02401..ec56da2 100644
--- a/c/enc/encode.c
+++ b/c/enc/encode.c
@@ -117,7 +117,6 @@
 static BROTLI_BOOL EnsureInitialized(BrotliEncoderState* s);
 
 static size_t InputBlockSize(BrotliEncoderState* s) {
-  if (!EnsureInitialized(s)) return 0;
   return (size_t)1 << s->params.lgblock;
 }
 
@@ -817,7 +816,6 @@
                                   const uint8_t* input_buffer) {
   RingBuffer* ringbuffer_ = &s->ringbuffer_;
   MemoryManager* m = &s->memory_manager_;
-  if (!EnsureInitialized(s)) return;
   RingBufferWrite(m, input_buffer, input_size, ringbuffer_);
   if (BROTLI_IS_OOM(m)) return;
   s->input_pos_ += input_size;
@@ -933,7 +931,6 @@
   MemoryManager* m = &s->memory_manager_;
   ContextType literal_context_mode;
 
-  if (!EnsureInitialized(s)) return BROTLI_FALSE;
   data = s->ringbuffer_.buffer_;
   mask = s->ringbuffer_.mask_;
 
diff --git a/c/enc/static_dict.c b/c/enc/static_dict.c
index 758ef80..7299ab7 100644
--- a/c/enc/static_dict.c
+++ b/c/enc/static_dict.c
@@ -16,11 +16,6 @@
 extern "C" {
 #endif
 
-/* TODO: use BrotliTransforms.cutOffTransforms instead. */
-static const uint8_t kOmitLastNTransforms[10] = {
-  0, 12, 27, 23, 42, 63, 56, 48, 59, 64,
-};
-
 static BROTLI_INLINE uint32_t Hash(const uint8_t* data) {
   uint32_t h = BROTLI_UNALIGNED_LOAD32LE(data) * kDictHashMul32;
   /* The higher bits contain more mixture from the multiplication,
@@ -121,7 +116,10 @@
         if (l > 9) minlen = BROTLI_MAX(size_t, minlen, l - 9);
         maxlen = BROTLI_MIN(size_t, matchlen, l - 2);
         for (len = minlen; len <= maxlen; ++len) {
-          AddMatch(id + kOmitLastNTransforms[l - len] * n, len, l, matches);
+          size_t cut = l - len;
+          size_t transform_id = (cut << 2) +
+              (size_t)((dictionary->cutoffTransforms >> (cut * 6)) & 0x3F);
+          AddMatch(id + transform_id * n, len, l, matches);
           has_found_match = BROTLI_TRUE;
         }
         if (matchlen < l || l + 6 >= max_length) {
diff --git a/java/org/brotli/wrapper/dec/BrotliInputStream.java b/java/org/brotli/wrapper/dec/BrotliInputStream.java
index 76bcf1d..26f7a82 100644
--- a/java/org/brotli/wrapper/dec/BrotliInputStream.java
+++ b/java/org/brotli/wrapper/dec/BrotliInputStream.java
@@ -53,7 +53,16 @@
     if (decoder.closed) {
       throw new IOException("read after close");
     }
-    if (decoder.decode() == -1) {
+    int decoded;
+    // Iterate until at leat one byte is decoded, or EOF reached.
+    while (true) {
+      decoded = decoder.decode();
+      if (decoded != 0) {
+        break;
+      }
+    }
+
+    if (decoded == -1) {
       return -1;
     }
     return decoder.buffer.get() & 0xFF;
diff --git a/java/org/brotli/wrapper/dec/Decoder.java b/java/org/brotli/wrapper/dec/Decoder.java
index 0326403..548c14d 100644
--- a/java/org/brotli/wrapper/dec/Decoder.java
+++ b/java/org/brotli/wrapper/dec/Decoder.java
@@ -15,6 +15,7 @@
  * Base class for InputStream / Channel implementations.
  */
 public class Decoder {
+  private static final ByteBuffer EMPTY_BUFER = ByteBuffer.allocate(0);
   private final ReadableByteChannel source;
   private final DecoderJNI.Wrapper decoder;
   ByteBuffer buffer;
@@ -87,6 +88,11 @@
           if (bytesRead == -1) {
             fail("unexpected end of input");
           }
+          if (bytesRead == 0) {
+            // No input data is currently available.
+            buffer = EMPTY_BUFER;
+            return 0;
+          }
           decoder.push(bytesRead);
           break;
 
diff --git a/research/draw_diff.cc b/research/draw_diff.cc
index 6541dac..1a52869 100644
--- a/research/draw_diff.cc
+++ b/research/draw_diff.cc
@@ -16,7 +16,7 @@
 #include <cstdlib>  /* exit, EXIT_FAILURE */
 #include <vector>
 
-#ifndef CHECK
+#if !defined(CHECK)
 #define CHECK(X) if (!(X)) exit(EXIT_FAILURE);
 #endif
 
diff --git a/research/read_dist.h b/research/read_dist.h
index 3cac473..63d3b97 100644
--- a/research/read_dist.h
+++ b/research/read_dist.h
@@ -19,7 +19,7 @@
 #include <cstdio>
 #include <cstdlib>  /* exit, EXIT_FAILURE */
 
-#ifndef CHECK
+#if !defined(CHECK)
 #define CHECK(X) if (!(X)) exit(EXIT_FAILURE);
 #endif