You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@hbase.apache.org by st...@apache.org on 2016/10/04 05:16:57 UTC

[44/51] [partial] hbase git commit: HBASE-15638 Shade protobuf Which includes

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/protobuf/ResponseConverter.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/protobuf/ResponseConverter.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/protobuf/ResponseConverter.java
deleted file mode 100644
index e5deabd..0000000
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/protobuf/ResponseConverter.java
+++ /dev/null
@@ -1,442 +0,0 @@
-/**
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.apache.hadoop.hbase.protobuf;
-
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-import edu.umd.cs.findbugs.annotations.Nullable;
-import org.apache.commons.logging.Log;
-import org.apache.commons.logging.LogFactory;
-import org.apache.hadoop.hbase.Cell;
-import org.apache.hadoop.hbase.CellScanner;
-import org.apache.hadoop.hbase.DoNotRetryIOException;
-import org.apache.hadoop.hbase.HRegionInfo;
-import org.apache.hadoop.hbase.ServerName;
-import org.apache.hadoop.hbase.classification.InterfaceAudience;
-import org.apache.hadoop.hbase.client.Result;
-import org.apache.hadoop.hbase.client.SingleResponse;
-import org.apache.hadoop.hbase.ipc.ServerRpcController;
-import org.apache.hadoop.hbase.protobuf.generated.AccessControlProtos.GetUserPermissionsResponse;
-import org.apache.hadoop.hbase.protobuf.generated.AdminProtos.CloseRegionResponse;
-import org.apache.hadoop.hbase.protobuf.generated.AdminProtos.GetOnlineRegionResponse;
-import org.apache.hadoop.hbase.protobuf.generated.AdminProtos.GetServerInfoResponse;
-import org.apache.hadoop.hbase.protobuf.generated.AdminProtos.OpenRegionResponse;
-import org.apache.hadoop.hbase.protobuf.generated.AdminProtos.ServerInfo;
-import org.apache.hadoop.hbase.protobuf.generated.ClientProtos;
-import org.apache.hadoop.hbase.protobuf.generated.ClientProtos.MultiRequest;
-import org.apache.hadoop.hbase.protobuf.generated.ClientProtos.MultiResponse;
-import org.apache.hadoop.hbase.protobuf.generated.ClientProtos.RegionAction;
-import org.apache.hadoop.hbase.protobuf.generated.ClientProtos.RegionActionResult;
-import org.apache.hadoop.hbase.protobuf.generated.ClientProtos.ResultOrException;
-import org.apache.hadoop.hbase.protobuf.generated.ClientProtos.ScanResponse;
-import org.apache.hadoop.hbase.protobuf.generated.ClusterStatusProtos.RegionStoreSequenceIds;
-import org.apache.hadoop.hbase.protobuf.generated.HBaseProtos;
-import org.apache.hadoop.hbase.protobuf.generated.HBaseProtos.NameBytesPair;
-import org.apache.hadoop.hbase.protobuf.generated.HBaseProtos.NameInt64Pair;
-import org.apache.hadoop.hbase.protobuf.generated.MapReduceProtos.ScanMetrics;
-import org.apache.hadoop.hbase.protobuf.generated.MasterProtos.EnableCatalogJanitorResponse;
-import org.apache.hadoop.hbase.protobuf.generated.MasterProtos.RunCatalogScanResponse;
-import org.apache.hadoop.hbase.protobuf.generated.RegionServerStatusProtos.GetLastFlushedSequenceIdResponse;
-import org.apache.hadoop.hbase.regionserver.RegionOpeningState;
-import org.apache.hadoop.hbase.security.access.UserPermission;
-import org.apache.hadoop.util.StringUtils;
-
-import com.google.protobuf.ByteString;
-import com.google.protobuf.RpcController;
-
-/**
- * Helper utility to build protocol buffer responses,
- * or retrieve data from protocol buffer responses.
- */
-@InterfaceAudience.Private
-public final class ResponseConverter {
-  private static final Log LOG = LogFactory.getLog(ResponseConverter.class);
-
-  private ResponseConverter() {
-  }
-
-// Start utilities for Client
-
-  /**
-   * Get the results from a protocol buffer MultiResponse
-   *
-   * @param request the protocol buffer MultiResponse to convert
-   * @param cells Cells to go with the passed in <code>proto</code>.  Can be null.
-   * @return the results that were in the MultiResponse (a Result or an Exception).
-   * @throws IOException
-   */
-  public static org.apache.hadoop.hbase.client.MultiResponse getResults(final MultiRequest request,
-      final MultiResponse response, final CellScanner cells)
-  throws IOException {
-    int requestRegionActionCount = request.getRegionActionCount();
-    int responseRegionActionResultCount = response.getRegionActionResultCount();
-    if (requestRegionActionCount != responseRegionActionResultCount) {
-      throw new IllegalStateException("Request mutation count=" + requestRegionActionCount +
-          " does not match response mutation result count=" + responseRegionActionResultCount);
-    }
-
-    org.apache.hadoop.hbase.client.MultiResponse results =
-      new org.apache.hadoop.hbase.client.MultiResponse();
-
-    for (int i = 0; i < responseRegionActionResultCount; i++) {
-      RegionAction actions = request.getRegionAction(i);
-      RegionActionResult actionResult = response.getRegionActionResult(i);
-      HBaseProtos.RegionSpecifier rs = actions.getRegion();
-      if (rs.hasType() &&
-          (rs.getType() != HBaseProtos.RegionSpecifier.RegionSpecifierType.REGION_NAME)){
-        throw new IllegalArgumentException(
-            "We support only encoded types for protobuf multi response.");
-      }
-      byte[] regionName = rs.getValue().toByteArray();
-
-      if (actionResult.hasException()) {
-        Throwable regionException =  ProtobufUtil.toException(actionResult.getException());
-        results.addException(regionName, regionException);
-        continue;
-      }
-
-      if (actions.getActionCount() != actionResult.getResultOrExceptionCount()) {
-        throw new IllegalStateException("actions.getActionCount=" + actions.getActionCount() +
-            ", actionResult.getResultOrExceptionCount=" +
-            actionResult.getResultOrExceptionCount() + " for region " + actions.getRegion());
-      }
-
-      for (ResultOrException roe : actionResult.getResultOrExceptionList()) {
-        Object responseValue;
-        if (roe.hasException()) {
-          responseValue = ProtobufUtil.toException(roe.getException());
-        } else if (roe.hasResult()) {
-          responseValue = ProtobufUtil.toResult(roe.getResult(), cells);
-        } else if (roe.hasServiceResult()) {
-          responseValue = roe.getServiceResult();
-        } else{
-          // Sometimes, the response is just "it was processed". Generally, this occurs for things
-          // like mutateRows where either we get back 'processed' (or not) and optionally some
-          // statistics about the regions we touched.
-          responseValue = response.getProcessed() ?
-                          ProtobufUtil.EMPTY_RESULT_EXISTS_TRUE :
-                          ProtobufUtil.EMPTY_RESULT_EXISTS_FALSE;
-        }
-        results.add(regionName, roe.getIndex(), responseValue);
-      }
-    }
-
-    if (response.hasRegionStatistics()) {
-      ClientProtos.MultiRegionLoadStats stats = response.getRegionStatistics();
-      for (int i = 0; i < stats.getRegionCount(); i++) {
-        results.addStatistic(stats.getRegion(i).getValue().toByteArray(), stats.getStat(i));
-      }
-    }
-
-    return results;
-  }
-
-
-  public static SingleResponse getResult(final ClientProtos.MutateRequest request,
-                                         final ClientProtos.MutateResponse response,
-                                         final CellScanner cells)
-      throws IOException {
-    SingleResponse singleResponse = new SingleResponse();
-    SingleResponse.Entry entry = new SingleResponse.Entry();
-    entry.setResult(ProtobufUtil.toResult(response.getResult(), cells));
-    entry.setProcessed(response.getProcessed());
-    singleResponse.setEntry(entry);
-    return singleResponse;
-  }
-
-  /**
-   * Wrap a throwable to an action result.
-   *
-   * @param t
-   * @return an action result builder
-   */
-  public static ResultOrException.Builder buildActionResult(final Throwable t) {
-    ResultOrException.Builder builder = ResultOrException.newBuilder();
-    if (t != null) builder.setException(buildException(t));
-    return builder;
-  }
-
-  /**
-   * Wrap a throwable to an action result.
-   *
-   * @param r
-   * @return an action result builder
-   */
-  public static ResultOrException.Builder buildActionResult(final ClientProtos.Result r) {
-    ResultOrException.Builder builder = ResultOrException.newBuilder();
-    if (r != null) builder.setResult(r);
-    return builder;
-  }
-
-  /**
-   * @param t
-   * @return NameValuePair of the exception name to stringified version os exception.
-   */
-  public static NameBytesPair buildException(final Throwable t) {
-    NameBytesPair.Builder parameterBuilder = NameBytesPair.newBuilder();
-    parameterBuilder.setName(t.getClass().getName());
-    parameterBuilder.setValue(
-      ByteString.copyFromUtf8(StringUtils.stringifyException(t)));
-    return parameterBuilder.build();
-  }
-
-  /**
-   * Converts the permissions list into a protocol buffer GetUserPermissionsResponse
-   */
-  public static GetUserPermissionsResponse buildGetUserPermissionsResponse(
-      final List<UserPermission> permissions) {
-    GetUserPermissionsResponse.Builder builder = GetUserPermissionsResponse.newBuilder();
-    for (UserPermission perm : permissions) {
-      builder.addUserPermission(ProtobufUtil.toUserPermission(perm));
-    }
-    return builder.build();
-  }
-
-// End utilities for Client
-// Start utilities for Admin
-
-  /**
-   * Get the list of region info from a GetOnlineRegionResponse
-   *
-   * @param proto the GetOnlineRegionResponse
-   * @return the list of region info
-   */
-  public static List<HRegionInfo> getRegionInfos(final GetOnlineRegionResponse proto) {
-    if (proto == null || proto.getRegionInfoCount() == 0) return null;
-    return ProtobufUtil.getRegionInfos(proto);
-  }
-
-  /**
-   * Get the region opening state from a OpenRegionResponse
-   *
-   * @param proto the OpenRegionResponse
-   * @return the region opening state
-   */
-  public static RegionOpeningState getRegionOpeningState
-      (final OpenRegionResponse proto) {
-    if (proto == null || proto.getOpeningStateCount() != 1) return null;
-    return RegionOpeningState.valueOf(
-      proto.getOpeningState(0).name());
-  }
-
-  /**
-   * Get a list of region opening state from a OpenRegionResponse
-   * 
-   * @param proto the OpenRegionResponse
-   * @return the list of region opening state
-   */
-  public static List<RegionOpeningState> getRegionOpeningStateList(
-      final OpenRegionResponse proto) {
-    if (proto == null) return null;
-    List<RegionOpeningState> regionOpeningStates = new ArrayList<RegionOpeningState>();
-    for (int i = 0; i < proto.getOpeningStateCount(); i++) {
-      regionOpeningStates.add(RegionOpeningState.valueOf(
-          proto.getOpeningState(i).name()));
-    }
-    return regionOpeningStates;
-  }
-
-  /**
-   * Check if the region is closed from a CloseRegionResponse
-   *
-   * @param proto the CloseRegionResponse
-   * @return the region close state
-   */
-  public static boolean isClosed
-      (final CloseRegionResponse proto) {
-    if (proto == null || !proto.hasClosed()) return false;
-    return proto.getClosed();
-  }
-
-  /**
-   * A utility to build a GetServerInfoResponse.
-   *
-   * @param serverName
-   * @param webuiPort
-   * @return the response
-   */
-  public static GetServerInfoResponse buildGetServerInfoResponse(
-      final ServerName serverName, final int webuiPort) {
-    GetServerInfoResponse.Builder builder = GetServerInfoResponse.newBuilder();
-    ServerInfo.Builder serverInfoBuilder = ServerInfo.newBuilder();
-    serverInfoBuilder.setServerName(ProtobufUtil.toServerName(serverName));
-    if (webuiPort >= 0) {
-      serverInfoBuilder.setWebuiPort(webuiPort);
-    }
-    builder.setServerInfo(serverInfoBuilder.build());
-    return builder.build();
-  }
-
-  /**
-   * A utility to build a GetOnlineRegionResponse.
-   *
-   * @param regions
-   * @return the response
-   */
-  public static GetOnlineRegionResponse buildGetOnlineRegionResponse(
-      final List<HRegionInfo> regions) {
-    GetOnlineRegionResponse.Builder builder = GetOnlineRegionResponse.newBuilder();
-    for (HRegionInfo region: regions) {
-      builder.addRegionInfo(HRegionInfo.convert(region));
-    }
-    return builder.build();
-  }
-
-  /**
-   * Creates a response for the catalog scan request
-   * @return A RunCatalogScanResponse
-   */
-  public static RunCatalogScanResponse buildRunCatalogScanResponse(int numCleaned) {
-    return RunCatalogScanResponse.newBuilder().setScanResult(numCleaned).build();
-  }
-
-  /**
-   * Creates a response for the catalog scan request
-   * @return A EnableCatalogJanitorResponse
-   */
-  public static EnableCatalogJanitorResponse buildEnableCatalogJanitorResponse(boolean prevValue) {
-    return EnableCatalogJanitorResponse.newBuilder().setPrevValue(prevValue).build();
-  }
-
-// End utilities for Admin
-
-  /**
-   * Creates a response for the last flushed sequence Id request
-   * @return A GetLastFlushedSequenceIdResponse
-   */
-  public static GetLastFlushedSequenceIdResponse buildGetLastFlushedSequenceIdResponse(
-      RegionStoreSequenceIds ids) {
-    return GetLastFlushedSequenceIdResponse.newBuilder()
-        .setLastFlushedSequenceId(ids.getLastFlushedSequenceId())
-        .addAllStoreLastFlushedSequenceId(ids.getStoreSequenceIdList()).build();
-  }
-
-  /**
-   * Stores an exception encountered during RPC invocation so it can be passed back
-   * through to the client.
-   * @param controller the controller instance provided by the client when calling the service
-   * @param ioe the exception encountered
-   */
-  public static void setControllerException(RpcController controller, IOException ioe) {
-    if (controller != null) {
-      if (controller instanceof ServerRpcController) {
-        ((ServerRpcController)controller).setFailedOn(ioe);
-      } else {
-        controller.setFailed(StringUtils.stringifyException(ioe));
-      }
-    }
-  }
-
-  /**
-   * Retreivies exception stored during RPC invocation.
-   * @param controller the controller instance provided by the client when calling the service
-   * @return exception if any, or null; Will return DoNotRetryIOException for string represented
-   * failure causes in controller.
-   */
-  @Nullable
-  public static IOException getControllerException(RpcController controller) throws IOException {
-    if (controller != null && controller.failed()) {
-      if (controller instanceof ServerRpcController) {
-        return ((ServerRpcController)controller).getFailedOn();
-      } else {
-        return new DoNotRetryIOException(controller.errorText());
-      }
-    }
-    return null;
-  }
-
-
-  /**
-   * Create Results from the cells using the cells meta data. 
-   * @param cellScanner
-   * @param response
-   * @return results
-   */
-  public static Result[] getResults(CellScanner cellScanner, ScanResponse response)
-      throws IOException {
-    if (response == null) return null;
-    // If cellscanner, then the number of Results to return is the count of elements in the
-    // cellsPerResult list.  Otherwise, it is how many results are embedded inside the response.
-    int noOfResults = cellScanner != null?
-      response.getCellsPerResultCount(): response.getResultsCount();
-    Result[] results = new Result[noOfResults];
-    for (int i = 0; i < noOfResults; i++) {
-      if (cellScanner != null) {
-        // Cells are out in cellblocks.  Group them up again as Results.  How many to read at a
-        // time will be found in getCellsLength -- length here is how many Cells in the i'th Result
-        int noOfCells = response.getCellsPerResult(i);
-        boolean isPartial =
-            response.getPartialFlagPerResultCount() > i ?
-                response.getPartialFlagPerResult(i) : false;
-        List<Cell> cells = new ArrayList<Cell>(noOfCells);
-        for (int j = 0; j < noOfCells; j++) {
-          try {
-            if (cellScanner.advance() == false) {
-              // We are not able to retrieve the exact number of cells which ResultCellMeta says us.
-              // We have to scan for the same results again. Throwing DNRIOE as a client retry on the
-              // same scanner will result in OutOfOrderScannerNextException
-              String msg = "Results sent from server=" + noOfResults + ". But only got " + i
-                + " results completely at client. Resetting the scanner to scan again.";
-              LOG.error(msg);
-              throw new DoNotRetryIOException(msg);
-            }
-          } catch (IOException ioe) {
-            // We are getting IOE while retrieving the cells for Results.
-            // We have to scan for the same results again. Throwing DNRIOE as a client retry on the
-            // same scanner will result in OutOfOrderScannerNextException
-            LOG.error("Exception while reading cells from result."
-              + "Resetting the scanner to scan again.", ioe);
-            throw new DoNotRetryIOException("Resetting the scanner.", ioe);
-          }
-          cells.add(cellScanner.current());
-        }
-        results[i] = Result.create(cells, null, response.getStale(), isPartial);
-      } else {
-        // Result is pure pb.
-        results[i] = ProtobufUtil.toResult(response.getResults(i));
-      }
-    }
-    return results;
-  }
-
-  public static Map<String, Long> getScanMetrics(ScanResponse response) {
-    Map<String, Long> metricMap = new HashMap<String, Long>();
-    if (response == null || !response.hasScanMetrics() || response.getScanMetrics() == null) {
-      return metricMap;
-    }
-    
-    ScanMetrics metrics = response.getScanMetrics();
-    int numberOfMetrics = metrics.getMetricsCount();
-    for (int i = 0; i < numberOfMetrics; i++) {
-      NameInt64Pair metricPair = metrics.getMetrics(i);
-      if (metricPair != null) {
-        String name = metricPair.getName();
-        Long value = metricPair.getValue();
-        if (name != null && value != null) {
-          metricMap.put(name, value);
-        }
-      }
-    }
-
-    return metricMap;
-  }
-}

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaRetriever.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaRetriever.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaRetriever.java
index 68c8e0a..37e4a92 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaRetriever.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaRetriever.java
@@ -36,7 +36,7 @@ import org.apache.hadoop.hbase.client.Result;
 import org.apache.hadoop.hbase.client.ResultScanner;
 import org.apache.hadoop.hbase.client.Scan;
 import org.apache.hadoop.hbase.client.Table;
-import org.apache.hadoop.hbase.protobuf.generated.QuotaProtos.Quotas;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.QuotaProtos.Quotas;
 import org.apache.hadoop.util.StringUtils;
 
 /**

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaSettings.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaSettings.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaSettings.java
index 592c4db..ac6a396 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaSettings.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaSettings.java
@@ -22,8 +22,8 @@ import java.util.concurrent.TimeUnit;
 import org.apache.hadoop.hbase.TableName;
 import org.apache.hadoop.hbase.classification.InterfaceAudience;
 import org.apache.hadoop.hbase.classification.InterfaceStability;
-import org.apache.hadoop.hbase.protobuf.ProtobufUtil;
-import org.apache.hadoop.hbase.protobuf.generated.MasterProtos.SetQuotaRequest;
+import org.apache.hadoop.hbase.shaded.protobuf.ProtobufUtil;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.MasterProtos.SetQuotaRequest;
 
 @InterfaceAudience.Public
 @InterfaceStability.Evolving

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaSettingsFactory.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaSettingsFactory.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaSettingsFactory.java
index c9f2aaa..a7c49b3 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaSettingsFactory.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaSettingsFactory.java
@@ -24,10 +24,10 @@ import java.util.concurrent.TimeUnit;
 import org.apache.hadoop.hbase.TableName;
 import org.apache.hadoop.hbase.classification.InterfaceAudience;
 import org.apache.hadoop.hbase.classification.InterfaceStability;
-import org.apache.hadoop.hbase.protobuf.ProtobufUtil;
-import org.apache.hadoop.hbase.protobuf.generated.MasterProtos.SetQuotaRequest;
-import org.apache.hadoop.hbase.protobuf.generated.QuotaProtos;
-import org.apache.hadoop.hbase.protobuf.generated.QuotaProtos.Quotas;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.MasterProtos.SetQuotaRequest;
+import org.apache.hadoop.hbase.shaded.protobuf.ProtobufUtil;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.QuotaProtos;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.QuotaProtos.Quotas;
 
 @InterfaceAudience.Public
 @InterfaceStability.Evolving

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaTableUtil.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaTableUtil.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaTableUtil.java
index a8fec87..116dd0c 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaTableUtil.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/QuotaTableUtil.java
@@ -43,7 +43,7 @@ import org.apache.hadoop.hbase.filter.QualifierFilter;
 import org.apache.hadoop.hbase.filter.RegexStringComparator;
 import org.apache.hadoop.hbase.filter.RowFilter;
 import org.apache.hadoop.hbase.protobuf.ProtobufMagic;
-import org.apache.hadoop.hbase.protobuf.generated.QuotaProtos.Quotas;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.QuotaProtos.Quotas;
 import org.apache.hadoop.hbase.util.Bytes;
 import org.apache.hadoop.hbase.util.Strings;
 
@@ -409,4 +409,4 @@ public class QuotaTableUtil {
   protected static String getUserFromRowKey(final byte[] key) {
     return Bytes.toString(key, QUOTA_USER_ROW_KEY_PREFIX.length);
   }
-}
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/ThrottleSettings.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/ThrottleSettings.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/ThrottleSettings.java
index 519372d..476f620 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/ThrottleSettings.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/quotas/ThrottleSettings.java
@@ -22,9 +22,9 @@ import java.util.concurrent.TimeUnit;
 import org.apache.hadoop.hbase.TableName;
 import org.apache.hadoop.hbase.classification.InterfaceAudience;
 import org.apache.hadoop.hbase.classification.InterfaceStability;
-import org.apache.hadoop.hbase.protobuf.ProtobufUtil;
-import org.apache.hadoop.hbase.protobuf.generated.MasterProtos.SetQuotaRequest;
-import org.apache.hadoop.hbase.protobuf.generated.QuotaProtos;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.MasterProtos.SetQuotaRequest;
+import org.apache.hadoop.hbase.shaded.protobuf.ProtobufUtil;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.QuotaProtos;
 
 @InterfaceAudience.Private
 @InterfaceStability.Evolving

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeerConfig.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeerConfig.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeerConfig.java
index 1f0d085..64f6d1b 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeerConfig.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeerConfig.java
@@ -28,7 +28,6 @@ import java.util.TreeMap;
 import org.apache.hadoop.hbase.TableName;
 import org.apache.hadoop.hbase.classification.InterfaceAudience;
 import org.apache.hadoop.hbase.classification.InterfaceStability;
-import org.apache.hadoop.hbase.protobuf.generated.ZooKeeperProtos;
 import org.apache.hadoop.hbase.util.Bytes;
 
 /**

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeerZKImpl.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeerZKImpl.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeerZKImpl.java
index cfe543a..ce20e61 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeerZKImpl.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeerZKImpl.java
@@ -33,8 +33,8 @@ import org.apache.hadoop.hbase.TableName;
 import org.apache.hadoop.hbase.classification.InterfaceAudience;
 import org.apache.hadoop.hbase.client.replication.ReplicationSerDeHelper;
 import org.apache.hadoop.hbase.exceptions.DeserializationException;
-import org.apache.hadoop.hbase.protobuf.ProtobufUtil;
-import org.apache.hadoop.hbase.protobuf.generated.ZooKeeperProtos;
+import org.apache.hadoop.hbase.shaded.protobuf.ProtobufUtil;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.ZooKeeperProtos;
 import org.apache.hadoop.hbase.zookeeper.ZKUtil;
 import org.apache.hadoop.hbase.zookeeper.ZooKeeperNodeTracker;
 import org.apache.hadoop.hbase.zookeeper.ZooKeeperWatcher;

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeersZKImpl.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeersZKImpl.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeersZKImpl.java
index d4b93c0..d12c4e9 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeersZKImpl.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationPeersZKImpl.java
@@ -38,7 +38,7 @@ import org.apache.hadoop.hbase.TableName;
 import org.apache.hadoop.hbase.classification.InterfaceAudience;
 import org.apache.hadoop.hbase.client.replication.ReplicationSerDeHelper;
 import org.apache.hadoop.hbase.exceptions.DeserializationException;
-import org.apache.hadoop.hbase.protobuf.generated.ZooKeeperProtos;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.ZooKeeperProtos;
 import org.apache.hadoop.hbase.replication.ReplicationPeer.PeerState;
 import org.apache.hadoop.hbase.util.Pair;
 import org.apache.hadoop.hbase.zookeeper.ZKConfig;

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationQueuesZKImpl.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationQueuesZKImpl.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationQueuesZKImpl.java
index 40c9140..ae7b3d6 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationQueuesZKImpl.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationQueuesZKImpl.java
@@ -30,6 +30,8 @@ import org.apache.hadoop.conf.Configuration;
 import org.apache.hadoop.hbase.Abortable;
 import org.apache.hadoop.hbase.HConstants;
 import org.apache.hadoop.hbase.exceptions.DeserializationException;
+import org.apache.hadoop.hbase.shaded.protobuf.ProtobufUtil;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.ZooKeeperProtos;
 import org.apache.hadoop.hbase.util.Bytes;
 import org.apache.hadoop.hbase.util.Pair;
 import org.apache.hadoop.hbase.zookeeper.ZKUtil;

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationStateZKBase.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationStateZKBase.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationStateZKBase.java
index 79853a8..8fc7c07 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationStateZKBase.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/replication/ReplicationStateZKBase.java
@@ -18,14 +18,18 @@
  */
 package org.apache.hadoop.hbase.replication;
 
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
 import java.util.List;
 
 import com.google.common.annotations.VisibleForTesting;
+import org.apache.hadoop.hbase.shaded.com.google.protobuf.CodedOutputStream;
+
 import org.apache.hadoop.conf.Configuration;
 import org.apache.hadoop.hbase.Abortable;
 import org.apache.hadoop.hbase.classification.InterfaceAudience;
-import org.apache.hadoop.hbase.protobuf.ProtobufUtil;
-import org.apache.hadoop.hbase.protobuf.generated.ZooKeeperProtos;
+import org.apache.hadoop.hbase.shaded.protobuf.ProtobufUtil;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.ZooKeeperProtos;
 import org.apache.hadoop.hbase.zookeeper.ZKConfig;
 import org.apache.hadoop.hbase.zookeeper.ZKUtil;
 import org.apache.hadoop.hbase.zookeeper.ZooKeeperWatcher;
@@ -106,9 +110,19 @@ public abstract class ReplicationStateZKBase {
    *         /hbase/replication/peers/PEER_ID/peer-state.
    */
   protected static byte[] toByteArray(final ZooKeeperProtos.ReplicationState.State state) {
-    byte[] bytes =
-        ZooKeeperProtos.ReplicationState.newBuilder().setState(state).build().toByteArray();
-    return ProtobufUtil.prependPBMagic(bytes);
+    ZooKeeperProtos.ReplicationState msg =
+        ZooKeeperProtos.ReplicationState.newBuilder().setState(state).build();
+    // There is no toByteArray on this pb Message?
+    // 32 bytes is default which seems fair enough here.
+    try (ByteArrayOutputStream baos = new ByteArrayOutputStream()) {
+      CodedOutputStream cos = CodedOutputStream.newInstance(baos, 16);
+      msg.writeTo(cos);
+      cos.flush();
+      baos.flush();
+      return ProtobufUtil.prependPBMagic(baos.toByteArray());
+    } catch (IOException e) {
+      throw new RuntimeException(e);
+    }
   }
 
   protected boolean peerExists(String id) throws KeeperException {

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/security/EncryptionUtil.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/security/EncryptionUtil.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/security/EncryptionUtil.java
index d89d96c..b5009e0 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/security/EncryptionUtil.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/security/EncryptionUtil.java
@@ -35,8 +35,8 @@ import org.apache.hadoop.hbase.classification.InterfaceAudience;
 import org.apache.hadoop.hbase.classification.InterfaceStability;
 import org.apache.hadoop.hbase.io.crypto.Cipher;
 import org.apache.hadoop.hbase.io.crypto.Encryption;
-import org.apache.hadoop.hbase.protobuf.generated.EncryptionProtos;
-import org.apache.hadoop.hbase.util.ByteStringer;
+import org.apache.hadoop.hbase.shaded.com.google.protobuf.UnsafeByteOperations;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.EncryptionProtos;
 import org.apache.hadoop.hbase.util.Bytes;
 
 /**
@@ -94,15 +94,15 @@ public final class EncryptionUtil {
     if (cipher.getIvLength() > 0) {
       iv = new byte[cipher.getIvLength()];
       RNG.nextBytes(iv);
-      builder.setIv(ByteStringer.wrap(iv));
+      builder.setIv(UnsafeByteOperations.unsafeWrap(iv));
     }
     byte[] keyBytes = key.getEncoded();
     builder.setLength(keyBytes.length);
-    builder.setHash(ByteStringer.wrap(Encryption.hash128(keyBytes)));
+    builder.setHash(UnsafeByteOperations.unsafeWrap(Encryption.hash128(keyBytes)));
     ByteArrayOutputStream out = new ByteArrayOutputStream();
     Encryption.encryptWithSubjectKey(out, new ByteArrayInputStream(keyBytes), subject,
       conf, cipher, iv);
-    builder.setData(ByteStringer.wrap(out.toByteArray()));
+    builder.setData(UnsafeByteOperations.unsafeWrap(out.toByteArray()));
     // Build and return the protobuf message
     out.reset();
     builder.build().writeDelimitedTo(out);

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/security/SecurityInfo.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/security/SecurityInfo.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/security/SecurityInfo.java
index eca54a4..e48f81d 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/security/SecurityInfo.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/security/SecurityInfo.java
@@ -21,11 +21,11 @@ import java.util.concurrent.ConcurrentHashMap;
 import java.util.concurrent.ConcurrentMap;
 
 import org.apache.hadoop.hbase.classification.InterfaceAudience;
-import org.apache.hadoop.hbase.protobuf.generated.AdminProtos;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.AdminProtos;
 import org.apache.hadoop.hbase.protobuf.generated.AuthenticationProtos.TokenIdentifier.Kind;
-import org.apache.hadoop.hbase.protobuf.generated.ClientProtos;
-import org.apache.hadoop.hbase.protobuf.generated.MasterProtos.MasterService;
-import org.apache.hadoop.hbase.protobuf.generated.RegionServerStatusProtos;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.ClientProtos;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.MasterProtos.MasterService;
+import org.apache.hadoop.hbase.shaded.protobuf.generated.RegionServerStatusProtos;
 
 /**
  * Maps RPC protocol interfaces to required configuration

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/security/access/AccessControlClient.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/security/access/AccessControlClient.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/security/access/AccessControlClient.java
index edbd0a3..96db2d1 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/security/access/AccessControlClient.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/security/access/AccessControlClient.java
@@ -31,13 +31,10 @@ import org.apache.hadoop.hbase.ZooKeeperConnectionException;
 import org.apache.hadoop.hbase.classification.InterfaceAudience;
 import org.apache.hadoop.hbase.classification.InterfaceStability;
 import org.apache.hadoop.hbase.client.Admin;
-import org.apache.hadoop.hbase.client.ClusterConnection;
 import org.apache.hadoop.hbase.client.Connection;
 import org.apache.hadoop.hbase.client.Table;
 import org.apache.hadoop.hbase.client.security.SecurityCapability;
 import org.apache.hadoop.hbase.ipc.CoprocessorRpcChannel;
-import org.apache.hadoop.hbase.ipc.HBaseRpcController;
-import org.apache.hadoop.hbase.protobuf.ProtobufUtil;
 import org.apache.hadoop.hbase.protobuf.generated.AccessControlProtos;
 import org.apache.hadoop.hbase.protobuf.generated.AccessControlProtos.AccessControlService.BlockingInterface;
 import org.apache.hadoop.hbase.util.Bytes;
@@ -94,11 +91,13 @@ public class AccessControlClient {
   public static void grant(Connection connection, final TableName tableName,
       final String userName, final byte[] family, final byte[] qual,
       final Permission.Action... actions) throws Throwable {
+    /* TODO: Priority is not used.
     HBaseRpcController controller
       = ((ClusterConnection) connection).getRpcControllerFactory().newController();
     controller.setPriority(tableName);
+    */
     try (Table table = connection.getTable(ACL_TABLE_NAME)) {
-      ProtobufUtil.grant(controller, getAccessControlServiceStub(table), userName, tableName,
+      AccessControlUtil.grant(null, getAccessControlServiceStub(table), userName, tableName,
         family, qual, actions);
     }
   }
@@ -113,11 +112,12 @@ public class AccessControlClient {
    */
   public static void grant(Connection connection, final String namespace,
       final String userName, final Permission.Action... actions) throws Throwable {
+    /* TODO: Pass an rpcController.
     HBaseRpcController controller
       = ((ClusterConnection) connection).getRpcControllerFactory().newController();
-
+    */
     try (Table table = connection.getTable(ACL_TABLE_NAME)) {
-      ProtobufUtil.grant(controller, getAccessControlServiceStub(table), userName, namespace,
+      AccessControlUtil.grant(null, getAccessControlServiceStub(table), userName, namespace,
         actions);
     }
   }
@@ -128,10 +128,12 @@ public class AccessControlClient {
    */
   public static void grant(Connection connection, final String userName,
        final Permission.Action... actions) throws Throwable {
+    /* TODO: Pass an rpcController
     HBaseRpcController controller
       = ((ClusterConnection) connection).getRpcControllerFactory().newController();
+    */
     try (Table table = connection.getTable(ACL_TABLE_NAME)) {
-      ProtobufUtil.grant(controller, getAccessControlServiceStub(table), userName, actions);
+      AccessControlUtil.grant(null, getAccessControlServiceStub(table), userName, actions);
     }
   }
 
@@ -155,11 +157,13 @@ public class AccessControlClient {
   public static void revoke(Connection connection, final TableName tableName,
       final String username, final byte[] family, final byte[] qualifier,
       final Permission.Action... actions) throws Throwable {
+    /** TODO: Pass an rpcController
     HBaseRpcController controller
       = ((ClusterConnection) connection).getRpcControllerFactory().newController();
     controller.setPriority(tableName);
+    */
     try (Table table = connection.getTable(ACL_TABLE_NAME)) {
-      ProtobufUtil.revoke(controller, getAccessControlServiceStub(table), username, tableName,
+      AccessControlUtil.revoke(null, getAccessControlServiceStub(table), username, tableName,
         family, qualifier, actions);
     }
   }
@@ -174,10 +178,12 @@ public class AccessControlClient {
    */
   public static void revoke(Connection connection, final String namespace,
       final String userName, final Permission.Action... actions) throws Throwable {
+    /** TODO: Pass an rpcController
     HBaseRpcController controller
       = ((ClusterConnection) connection).getRpcControllerFactory().newController();
+      */
     try (Table table = connection.getTable(ACL_TABLE_NAME)) {
-      ProtobufUtil.revoke(controller, getAccessControlServiceStub(table), userName, namespace,
+      AccessControlUtil.revoke(null, getAccessControlServiceStub(table), userName, namespace,
         actions);
     }
   }
@@ -188,10 +194,12 @@ public class AccessControlClient {
    */
   public static void revoke(Connection connection, final String userName,
       final Permission.Action... actions) throws Throwable {
+    /** TODO: Pass an rpc controller.
     HBaseRpcController controller
       = ((ClusterConnection) connection).getRpcControllerFactory().newController();
+      */
     try (Table table = connection.getTable(ACL_TABLE_NAME)) {
-      ProtobufUtil.revoke(controller, getAccessControlServiceStub(table), userName, actions);
+      AccessControlUtil.revoke(null, getAccessControlServiceStub(table), userName, actions);
     }
   }
 
@@ -206,8 +214,10 @@ public class AccessControlClient {
    */
   public static List<UserPermission> getUserPermissions(Connection connection, String tableRegex)
       throws Throwable {
+    /** TODO: Pass an rpcController
     HBaseRpcController controller
       = ((ClusterConnection) connection).getRpcControllerFactory().newController();
+      */
     List<UserPermission> permList = new ArrayList<UserPermission>();
     try (Table table = connection.getTable(ACL_TABLE_NAME)) {
       try (Admin admin = connection.getAdmin()) {
@@ -216,20 +226,20 @@ public class AccessControlClient {
             AccessControlProtos.AccessControlService.newBlockingStub(service);
         HTableDescriptor[] htds = null;
         if (tableRegex == null || tableRegex.isEmpty()) {
-          permList = ProtobufUtil.getUserPermissions(controller, protocol);
+          permList = AccessControlUtil.getUserPermissions(null, protocol);
         } else if (tableRegex.charAt(0) == '@') {  // Namespaces
           String namespaceRegex = tableRegex.substring(1);
           for (NamespaceDescriptor nsds : admin.listNamespaceDescriptors()) {  // Read out all namespaces
             String namespace = nsds.getName();
             if (namespace.matches(namespaceRegex)) {  // Match the given namespace regex?
-              permList.addAll(ProtobufUtil.getUserPermissions(controller, protocol,
+              permList.addAll(AccessControlUtil.getUserPermissions(null, protocol,
                 Bytes.toBytes(namespace)));
             }
           }
         } else {  // Tables
           htds = admin.listTables(Pattern.compile(tableRegex), true);
           for (HTableDescriptor hd : htds) {
-            permList.addAll(ProtobufUtil.getUserPermissions(controller, protocol,
+            permList.addAll(AccessControlUtil.getUserPermissions(null, protocol,
               hd.getTableName()));
           }
         }

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/security/access/AccessControlUtil.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/security/access/AccessControlUtil.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/security/access/AccessControlUtil.java
new file mode 100644
index 0000000..325edeb
--- /dev/null
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/security/access/AccessControlUtil.java
@@ -0,0 +1,766 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.hadoop.hbase.security.access;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.List;
+import java.util.Map;
+
+import org.apache.hadoop.hbase.TableName;
+import org.apache.hadoop.hbase.classification.InterfaceAudience;
+import org.apache.hadoop.hbase.protobuf.ProtobufUtil;
+import org.apache.hadoop.hbase.protobuf.generated.AccessControlProtos;
+import org.apache.hadoop.hbase.protobuf.generated.AccessControlProtos.AccessControlService;
+import org.apache.hadoop.hbase.protobuf.generated.AccessControlProtos.GetUserPermissionsResponse;
+
+import com.google.common.collect.ArrayListMultimap;
+import com.google.common.collect.ListMultimap;
+import com.google.common.collect.Lists;
+import com.google.protobuf.ByteString;
+import com.google.protobuf.RpcController;
+import com.google.protobuf.ServiceException;
+
+@InterfaceAudience.Private
+public class AccessControlUtil {
+  private AccessControlUtil() {}
+
+  /**
+   * Create a request to grant user permissions.
+   *
+   * @param username the short user name who to grant permissions
+   * @param tableName optional table name the permissions apply
+   * @param family optional column family
+   * @param qualifier optional qualifier
+   * @param actions the permissions to be granted
+   * @return A {@link AccessControlProtos} GrantRequest
+   */
+  public static AccessControlProtos.GrantRequest buildGrantRequest(
+      String username, TableName tableName, byte[] family, byte[] qualifier,
+      AccessControlProtos.Permission.Action... actions) {
+    AccessControlProtos.Permission.Builder ret =
+        AccessControlProtos.Permission.newBuilder();
+    AccessControlProtos.TablePermission.Builder permissionBuilder =
+        AccessControlProtos.TablePermission.newBuilder();
+    for (AccessControlProtos.Permission.Action a : actions) {
+      permissionBuilder.addAction(a);
+    }
+    if (tableName == null) {
+      throw new NullPointerException("TableName cannot be null");
+    }
+    permissionBuilder.setTableName(ProtobufUtil.toProtoTableName(tableName));
+
+    if (family != null) {
+      permissionBuilder.setFamily(ByteString.copyFrom(family));
+    }
+    if (qualifier != null) {
+      permissionBuilder.setQualifier(ByteString.copyFrom(qualifier));
+    }
+    ret.setType(AccessControlProtos.Permission.Type.Table)
+       .setTablePermission(permissionBuilder);
+    return AccessControlProtos.GrantRequest.newBuilder()
+      .setUserPermission(
+          AccessControlProtos.UserPermission.newBuilder()
+              .setUser(ByteString.copyFromUtf8(username))
+              .setPermission(ret)
+      ).build();
+  }
+
+  /**
+   * Create a request to grant user permissions.
+   *
+   * @param username the short user name who to grant permissions
+   * @param namespace optional table name the permissions apply
+   * @param actions the permissions to be granted
+   * @return A {@link AccessControlProtos} GrantRequest
+   */
+  public static AccessControlProtos.GrantRequest buildGrantRequest(
+      String username, String namespace,
+      AccessControlProtos.Permission.Action... actions) {
+    AccessControlProtos.Permission.Builder ret =
+        AccessControlProtos.Permission.newBuilder();
+    AccessControlProtos.NamespacePermission.Builder permissionBuilder =
+        AccessControlProtos.NamespacePermission.newBuilder();
+    for (AccessControlProtos.Permission.Action a : actions) {
+      permissionBuilder.addAction(a);
+    }
+    if (namespace != null) {
+      permissionBuilder.setNamespaceName(ByteString.copyFromUtf8(namespace));
+    }
+    ret.setType(AccessControlProtos.Permission.Type.Namespace)
+       .setNamespacePermission(permissionBuilder);
+    return AccessControlProtos.GrantRequest.newBuilder()
+      .setUserPermission(
+          AccessControlProtos.UserPermission.newBuilder()
+              .setUser(ByteString.copyFromUtf8(username))
+              .setPermission(ret)
+      ).build();
+  }
+
+  /**
+   * Create a request to revoke user permissions.
+   *
+   * @param username the short user name whose permissions to be revoked
+   * @param actions the permissions to be revoked
+   * @return A {@link AccessControlProtos} RevokeRequest
+   */
+  public static AccessControlProtos.RevokeRequest buildRevokeRequest(
+      String username, AccessControlProtos.Permission.Action... actions) {
+    AccessControlProtos.Permission.Builder ret =
+        AccessControlProtos.Permission.newBuilder();
+    AccessControlProtos.GlobalPermission.Builder permissionBuilder =
+        AccessControlProtos.GlobalPermission.newBuilder();
+    for (AccessControlProtos.Permission.Action a : actions) {
+      permissionBuilder.addAction(a);
+    }
+    ret.setType(AccessControlProtos.Permission.Type.Global)
+       .setGlobalPermission(permissionBuilder);
+    return AccessControlProtos.RevokeRequest.newBuilder()
+      .setUserPermission(
+          AccessControlProtos.UserPermission.newBuilder()
+              .setUser(ByteString.copyFromUtf8(username))
+              .setPermission(ret)
+      ).build();
+  }
+
+  /**
+   * Create a request to revoke user permissions.
+   *
+   * @param username the short user name whose permissions to be revoked
+   * @param namespace optional table name the permissions apply
+   * @param actions the permissions to be revoked
+   * @return A {@link AccessControlProtos} RevokeRequest
+   */
+  public static AccessControlProtos.RevokeRequest buildRevokeRequest(
+      String username, String namespace,
+      AccessControlProtos.Permission.Action... actions) {
+    AccessControlProtos.Permission.Builder ret =
+        AccessControlProtos.Permission.newBuilder();
+    AccessControlProtos.NamespacePermission.Builder permissionBuilder =
+        AccessControlProtos.NamespacePermission.newBuilder();
+    for (AccessControlProtos.Permission.Action a : actions) {
+      permissionBuilder.addAction(a);
+    }
+    if (namespace != null) {
+      permissionBuilder.setNamespaceName(ByteString.copyFromUtf8(namespace));
+    }
+    ret.setType(AccessControlProtos.Permission.Type.Namespace)
+       .setNamespacePermission(permissionBuilder);
+    return AccessControlProtos.RevokeRequest.newBuilder()
+      .setUserPermission(
+          AccessControlProtos.UserPermission.newBuilder()
+              .setUser(ByteString.copyFromUtf8(username))
+              .setPermission(ret)
+      ).build();
+  }
+
+  /**
+   * Create a request to grant user permissions.
+   *
+   * @param username the short user name who to grant permissions
+   * @param actions the permissions to be granted
+   * @return A {@link AccessControlProtos} GrantRequest
+   */
+  public static AccessControlProtos.GrantRequest buildGrantRequest(
+      String username, AccessControlProtos.Permission.Action... actions) {
+    AccessControlProtos.Permission.Builder ret =
+        AccessControlProtos.Permission.newBuilder();
+    AccessControlProtos.GlobalPermission.Builder permissionBuilder =
+        AccessControlProtos.GlobalPermission.newBuilder();
+    for (AccessControlProtos.Permission.Action a : actions) {
+      permissionBuilder.addAction(a);
+    }
+    ret.setType(AccessControlProtos.Permission.Type.Global)
+       .setGlobalPermission(permissionBuilder);
+    return AccessControlProtos.GrantRequest.newBuilder()
+      .setUserPermission(
+          AccessControlProtos.UserPermission.newBuilder()
+              .setUser(ByteString.copyFromUtf8(username))
+              .setPermission(ret)
+      ).build();
+  }
+
+  public static AccessControlProtos.UsersAndPermissions toUsersAndPermissions(String user,
+      Permission perms) {
+    return AccessControlProtos.UsersAndPermissions.newBuilder()
+        .addUserPermissions(AccessControlProtos.UsersAndPermissions.UserPermissions.newBuilder()
+            .setUser(ByteString.copyFromUtf8(user))
+            .addPermissions(toPermission(perms))
+            .build())
+        .build();
+  }
+
+  public static AccessControlProtos.UsersAndPermissions toUsersAndPermissions(
+      ListMultimap<String, Permission> perms) {
+    AccessControlProtos.UsersAndPermissions.Builder builder =
+        AccessControlProtos.UsersAndPermissions.newBuilder();
+    for (Map.Entry<String, Collection<Permission>> entry : perms.asMap().entrySet()) {
+      AccessControlProtos.UsersAndPermissions.UserPermissions.Builder userPermBuilder =
+          AccessControlProtos.UsersAndPermissions.UserPermissions.newBuilder();
+      userPermBuilder.setUser(ByteString.copyFromUtf8(entry.getKey()));
+      for (Permission perm: entry.getValue()) {
+        userPermBuilder.addPermissions(toPermission(perm));
+      }
+      builder.addUserPermissions(userPermBuilder.build());
+    }
+    return builder.build();
+  }
+
+  public static ListMultimap<String, Permission> toUsersAndPermissions(
+      AccessControlProtos.UsersAndPermissions proto) {
+    ListMultimap<String, Permission> result = ArrayListMultimap.create();
+    for (AccessControlProtos.UsersAndPermissions.UserPermissions userPerms:
+      proto.getUserPermissionsList()) {
+      String user = userPerms.getUser().toStringUtf8();
+      for (AccessControlProtos.Permission perm: userPerms.getPermissionsList()) {
+        result.put(user, toPermission(perm));
+      }
+    }
+    return result;
+  }
+
+
+  /**
+   * Converts a Permission proto to a client Permission object.
+   *
+   * @param proto the protobuf Permission
+   * @return the converted Permission
+   */
+  public static Permission toPermission(AccessControlProtos.Permission proto) {
+    if (proto.getType() != AccessControlProtos.Permission.Type.Global) {
+      return toTablePermission(proto);
+    } else {
+      List<Permission.Action> actions = toPermissionActions(
+          proto.getGlobalPermission().getActionList());
+      return new Permission(actions.toArray(new Permission.Action[actions.size()]));
+    }
+  }
+
+  /**
+   * Converts a Permission proto to a client TablePermission object.
+   *
+   * @param proto the protobuf Permission
+   * @return the converted TablePermission
+   */
+  public static TablePermission toTablePermission(AccessControlProtos.Permission proto) {
+    if(proto.getType() == AccessControlProtos.Permission.Type.Global) {
+      AccessControlProtos.GlobalPermission perm = proto.getGlobalPermission();
+      List<Permission.Action> actions = toPermissionActions(perm.getActionList());
+
+      return new TablePermission(null, null, null,
+          actions.toArray(new Permission.Action[actions.size()]));
+    }
+    if(proto.getType() == AccessControlProtos.Permission.Type.Namespace) {
+      AccessControlProtos.NamespacePermission perm = proto.getNamespacePermission();
+      List<Permission.Action> actions = toPermissionActions(perm.getActionList());
+
+      if(!proto.hasNamespacePermission()) {
+        throw new IllegalStateException("Namespace must not be empty in NamespacePermission");
+      }
+      String namespace = perm.getNamespaceName().toStringUtf8();
+      return new TablePermission(namespace, actions.toArray(new Permission.Action[actions.size()]));
+    }
+    if(proto.getType() == AccessControlProtos.Permission.Type.Table) {
+      AccessControlProtos.TablePermission perm = proto.getTablePermission();
+      List<Permission.Action> actions = toPermissionActions(perm.getActionList());
+
+      byte[] qualifier = null;
+      byte[] family = null;
+      TableName table = null;
+
+      if (!perm.hasTableName()) {
+        throw new IllegalStateException("TableName cannot be empty");
+      }
+      table = ProtobufUtil.toTableName(perm.getTableName());
+
+      if (perm.hasFamily()) family = perm.getFamily().toByteArray();
+      if (perm.hasQualifier()) qualifier = perm.getQualifier().toByteArray();
+
+      return new TablePermission(table, family, qualifier,
+          actions.toArray(new Permission.Action[actions.size()]));
+    }
+    throw new IllegalStateException("Unrecognize Perm Type: "+proto.getType());
+  }
+
+  /**
+   * Convert a client Permission to a Permission proto
+   *
+   * @param perm the client Permission
+   * @return the protobuf Permission
+   */
+  public static AccessControlProtos.Permission toPermission(Permission perm) {
+    AccessControlProtos.Permission.Builder ret = AccessControlProtos.Permission.newBuilder();
+    if (perm instanceof TablePermission) {
+      TablePermission tablePerm = (TablePermission)perm;
+      if(tablePerm.hasNamespace()) {
+        ret.setType(AccessControlProtos.Permission.Type.Namespace);
+
+        AccessControlProtos.NamespacePermission.Builder builder =
+            AccessControlProtos.NamespacePermission.newBuilder();
+        builder.setNamespaceName(ByteString.copyFromUtf8(tablePerm.getNamespace()));
+        Permission.Action[] actions = perm.getActions();
+        if (actions != null) {
+          for (Permission.Action a : actions) {
+            builder.addAction(toPermissionAction(a));
+          }
+        }
+        ret.setNamespacePermission(builder);
+        return ret.build();
+      } else if (tablePerm.hasTable()) {
+        ret.setType(AccessControlProtos.Permission.Type.Table);
+
+        AccessControlProtos.TablePermission.Builder builder =
+            AccessControlProtos.TablePermission.newBuilder();
+        builder.setTableName(ProtobufUtil.toProtoTableName(tablePerm.getTableName()));
+        if (tablePerm.hasFamily()) {
+          builder.setFamily(ByteString.copyFrom(tablePerm.getFamily()));
+        }
+        if (tablePerm.hasQualifier()) {
+          builder.setQualifier(ByteString.copyFrom(tablePerm.getQualifier()));
+        }
+        Permission.Action actions[] = perm.getActions();
+        if (actions != null) {
+          for (Permission.Action a : actions) {
+            builder.addAction(toPermissionAction(a));
+          }
+        }
+        ret.setTablePermission(builder);
+        return ret.build();
+      }
+    }
+
+    ret.setType(AccessControlProtos.Permission.Type.Global);
+
+    AccessControlProtos.GlobalPermission.Builder builder =
+        AccessControlProtos.GlobalPermission.newBuilder();
+    Permission.Action actions[] = perm.getActions();
+    if (actions != null) {
+      for (Permission.Action a: actions) {
+        builder.addAction(toPermissionAction(a));
+      }
+    }
+    ret.setGlobalPermission(builder);
+    return ret.build();
+  }
+
+  /**
+   * Converts a list of Permission.Action proto to a list of client Permission.Action objects.
+   *
+   * @param protoActions the list of protobuf Actions
+   * @return the converted list of Actions
+   */
+  public static List<Permission.Action> toPermissionActions(
+      List<AccessControlProtos.Permission.Action> protoActions) {
+    List<Permission.Action> actions = new ArrayList<Permission.Action>(protoActions.size());
+    for (AccessControlProtos.Permission.Action a : protoActions) {
+      actions.add(toPermissionAction(a));
+    }
+    return actions;
+  }
+
+  /**
+   * Converts a Permission.Action proto to a client Permission.Action object.
+   *
+   * @param action the protobuf Action
+   * @return the converted Action
+   */
+  public static Permission.Action toPermissionAction(
+      AccessControlProtos.Permission.Action action) {
+    switch (action) {
+    case READ:
+      return Permission.Action.READ;
+    case WRITE:
+      return Permission.Action.WRITE;
+    case EXEC:
+      return Permission.Action.EXEC;
+    case CREATE:
+      return Permission.Action.CREATE;
+    case ADMIN:
+      return Permission.Action.ADMIN;
+    }
+    throw new IllegalArgumentException("Unknown action value "+action.name());
+  }
+
+  /**
+   * Convert a client Permission.Action to a Permission.Action proto
+   *
+   * @param action the client Action
+   * @return the protobuf Action
+   */
+  public static AccessControlProtos.Permission.Action toPermissionAction(
+      Permission.Action action) {
+    switch (action) {
+    case READ:
+      return AccessControlProtos.Permission.Action.READ;
+    case WRITE:
+      return AccessControlProtos.Permission.Action.WRITE;
+    case EXEC:
+      return AccessControlProtos.Permission.Action.EXEC;
+    case CREATE:
+      return AccessControlProtos.Permission.Action.CREATE;
+    case ADMIN:
+      return AccessControlProtos.Permission.Action.ADMIN;
+    }
+    throw new IllegalArgumentException("Unknown action value "+action.name());
+  }
+
+  /**
+   * Convert a client user permission to a user permission proto
+   *
+   * @param perm the client UserPermission
+   * @return the protobuf UserPermission
+   */
+  public static AccessControlProtos.UserPermission toUserPermission(UserPermission perm) {
+    return AccessControlProtos.UserPermission.newBuilder()
+        .setUser(ByteString.copyFrom(perm.getUser()))
+        .setPermission(toPermission(perm))
+        .build();
+  }
+
+  /**
+   * Converts the permissions list into a protocol buffer GetUserPermissionsResponse
+   */
+  public static GetUserPermissionsResponse buildGetUserPermissionsResponse(
+      final List<UserPermission> permissions) {
+    GetUserPermissionsResponse.Builder builder = GetUserPermissionsResponse.newBuilder();
+    for (UserPermission perm : permissions) {
+      builder.addUserPermission(toUserPermission(perm));
+    }
+    return builder.build();
+  }
+
+  /**
+   * Converts a user permission proto to a client user permission object.
+   *
+   * @param proto the protobuf UserPermission
+   * @return the converted UserPermission
+   */
+  public static UserPermission toUserPermission(AccessControlProtos.UserPermission proto) {
+    return new UserPermission(proto.getUser().toByteArray(),
+        toTablePermission(proto.getPermission()));
+  }
+
+  /**
+   * Convert a ListMultimap&lt;String, TablePermission&gt; where key is username
+   * to a protobuf UserPermission
+   *
+   * @param perm the list of user and table permissions
+   * @return the protobuf UserTablePermissions
+   */
+  public static AccessControlProtos.UsersAndPermissions toUserTablePermissions(
+      ListMultimap<String, TablePermission> perm) {
+    AccessControlProtos.UsersAndPermissions.Builder builder =
+        AccessControlProtos.UsersAndPermissions.newBuilder();
+    for (Map.Entry<String, Collection<TablePermission>> entry : perm.asMap().entrySet()) {
+      AccessControlProtos.UsersAndPermissions.UserPermissions.Builder userPermBuilder =
+          AccessControlProtos.UsersAndPermissions.UserPermissions.newBuilder();
+      userPermBuilder.setUser(ByteString.copyFromUtf8(entry.getKey()));
+      for (TablePermission tablePerm: entry.getValue()) {
+        userPermBuilder.addPermissions(toPermission(tablePerm));
+      }
+      builder.addUserPermissions(userPermBuilder.build());
+    }
+    return builder.build();
+  }
+
+  /**
+   * A utility used to grant a user global permissions.
+   * <p>
+   * It's also called by the shell, in case you want to find references.
+   *
+   * @param protocol the AccessControlService protocol proxy
+   * @param userShortName the short name of the user to grant permissions
+   * @param actions the permissions to be granted
+   * @throws ServiceException
+   */
+  public static void grant(RpcController controller,
+      AccessControlService.BlockingInterface protocol, String userShortName,
+      Permission.Action... actions) throws ServiceException {
+    List<AccessControlProtos.Permission.Action> permActions =
+        Lists.newArrayListWithCapacity(actions.length);
+    for (Permission.Action a : actions) {
+      permActions.add(toPermissionAction(a));
+    }
+    AccessControlProtos.GrantRequest request = buildGrantRequest(userShortName,
+        permActions.toArray(new AccessControlProtos.Permission.Action[actions.length]));
+    protocol.grant(controller, request);
+  }
+
+  /**
+   * A utility used to grant a user table permissions. The permissions will
+   * be for a table table/column family/qualifier.
+   * <p>
+   * It's also called by the shell, in case you want to find references.
+   *
+   * @param protocol the AccessControlService protocol proxy
+   * @param userShortName the short name of the user to grant permissions
+   * @param tableName optional table name
+   * @param f optional column family
+   * @param q optional qualifier
+   * @param actions the permissions to be granted
+   * @throws ServiceException
+   */
+  public static void grant(RpcController controller,
+      AccessControlService.BlockingInterface protocol, String userShortName, TableName tableName,
+      byte[] f, byte[] q, Permission.Action... actions) throws ServiceException {
+    List<AccessControlProtos.Permission.Action> permActions =
+        Lists.newArrayListWithCapacity(actions.length);
+    for (Permission.Action a : actions) {
+      permActions.add(toPermissionAction(a));
+    }
+    AccessControlProtos.GrantRequest request = buildGrantRequest(userShortName, tableName, f, q,
+        permActions.toArray(new AccessControlProtos.Permission.Action[actions.length]));
+    protocol.grant(controller, request);
+  }
+
+  /**
+   * A utility used to grant a user namespace permissions.
+   * <p>
+   * It's also called by the shell, in case you want to find references.
+   *
+   * @param protocol the AccessControlService protocol proxy
+   * @param namespace the short name of the user to grant permissions
+   * @param actions the permissions to be granted
+   * @throws ServiceException
+   */
+  public static void grant(RpcController controller,
+      AccessControlService.BlockingInterface protocol, String userShortName, String namespace,
+      Permission.Action... actions) throws ServiceException {
+    List<AccessControlProtos.Permission.Action> permActions =
+        Lists.newArrayListWithCapacity(actions.length);
+    for (Permission.Action a : actions) {
+      permActions.add(toPermissionAction(a));
+    }
+    AccessControlProtos.GrantRequest request = buildGrantRequest(userShortName, namespace,
+        permActions.toArray(new AccessControlProtos.Permission.Action[actions.length]));
+    protocol.grant(controller, request);
+  }
+
+  /**
+   * A utility used to revoke a user's global permissions.
+   * <p>
+   * It's also called by the shell, in case you want to find references.
+   *
+   * @param protocol the AccessControlService protocol proxy
+   * @param userShortName the short name of the user to revoke permissions
+   * @param actions the permissions to be revoked
+   * @throws ServiceException
+   */
+  public static void revoke(RpcController controller,
+      AccessControlService.BlockingInterface protocol, String userShortName,
+      Permission.Action... actions) throws ServiceException {
+    List<AccessControlProtos.Permission.Action> permActions =
+        Lists.newArrayListWithCapacity(actions.length);
+    for (Permission.Action a : actions) {
+      permActions.add(toPermissionAction(a));
+    }
+    AccessControlProtos.RevokeRequest request = buildRevokeRequest(userShortName,
+        permActions.toArray(new AccessControlProtos.Permission.Action[actions.length]));
+    protocol.revoke(controller, request);
+  }
+
+  /**
+   * A utility used to revoke a user's table permissions. The permissions will
+   * be for a table/column family/qualifier.
+   * <p>
+   * It's also called by the shell, in case you want to find references.
+   *
+   * @param protocol the AccessControlService protocol proxy
+   * @param userShortName the short name of the user to revoke permissions
+   * @param tableName optional table name
+   * @param f optional column family
+   * @param q optional qualifier
+   * @param actions the permissions to be revoked
+   * @throws ServiceException
+   */
+  public static void revoke(RpcController controller,
+      AccessControlService.BlockingInterface protocol, String userShortName, TableName tableName,
+      byte[] f, byte[] q, Permission.Action... actions) throws ServiceException {
+    List<AccessControlProtos.Permission.Action> permActions =
+        Lists.newArrayListWithCapacity(actions.length);
+    for (Permission.Action a : actions) {
+      permActions.add(toPermissionAction(a));
+    }
+    AccessControlProtos.RevokeRequest request = buildRevokeRequest(userShortName, tableName, f, q,
+        permActions.toArray(new AccessControlProtos.Permission.Action[actions.length]));
+    protocol.revoke(controller, request);
+  }
+
+  /**
+   * A utility used to revoke a user's namespace permissions.
+   * <p>
+   * It's also called by the shell, in case you want to find references.
+   *
+   * @param protocol the AccessControlService protocol proxy
+   * @param userShortName the short name of the user to revoke permissions
+   * @param namespace optional table name
+   * @param actions the permissions to be revoked
+   * @throws ServiceException
+   */
+  public static void revoke(RpcController controller,
+      AccessControlService.BlockingInterface protocol, String userShortName, String namespace,
+      Permission.Action... actions) throws ServiceException {
+    List<AccessControlProtos.Permission.Action> permActions =
+        Lists.newArrayListWithCapacity(actions.length);
+    for (Permission.Action a : actions) {
+      permActions.add(toPermissionAction(a));
+    }
+    AccessControlProtos.RevokeRequest request = buildRevokeRequest(userShortName, namespace,
+        permActions.toArray(new AccessControlProtos.Permission.Action[actions.length]));
+    protocol.revoke(controller, request);
+  }
+
+  /**
+   * A utility used to get user's global permissions.
+   * <p>
+   * It's also called by the shell, in case you want to find references.
+   *
+   * @param protocol the AccessControlService protocol proxy
+   * @throws ServiceException
+   */
+  public static List<UserPermission> getUserPermissions(RpcController controller,
+      AccessControlService.BlockingInterface protocol) throws ServiceException {
+    AccessControlProtos.GetUserPermissionsRequest.Builder builder =
+        AccessControlProtos.GetUserPermissionsRequest.newBuilder();
+    builder.setType(AccessControlProtos.Permission.Type.Global);
+    AccessControlProtos.GetUserPermissionsRequest request = builder.build();
+    AccessControlProtos.GetUserPermissionsResponse response =
+        protocol.getUserPermissions(controller, request);
+    List<UserPermission> perms = new ArrayList<UserPermission>(response.getUserPermissionCount());
+    for (AccessControlProtos.UserPermission perm: response.getUserPermissionList()) {
+      perms.add(toUserPermission(perm));
+    }
+    return perms;
+  }
+
+  /**
+   * A utility used to get user table permissions.
+   * <p>
+   * It's also called by the shell, in case you want to find references.
+   *
+   * @param protocol the AccessControlService protocol proxy
+   * @param t optional table name
+   * @throws ServiceException
+   */
+  public static List<UserPermission> getUserPermissions(RpcController controller,
+      AccessControlService.BlockingInterface protocol,
+      TableName t) throws ServiceException {
+    AccessControlProtos.GetUserPermissionsRequest.Builder builder =
+        AccessControlProtos.GetUserPermissionsRequest.newBuilder();
+    if (t != null) {
+      builder.setTableName(ProtobufUtil.toProtoTableName(t));
+    }
+    builder.setType(AccessControlProtos.Permission.Type.Table);
+    AccessControlProtos.GetUserPermissionsRequest request = builder.build();
+    AccessControlProtos.GetUserPermissionsResponse response =
+        protocol.getUserPermissions(controller, request);
+    List<UserPermission> perms = new ArrayList<UserPermission>(response.getUserPermissionCount());
+    for (AccessControlProtos.UserPermission perm: response.getUserPermissionList()) {
+      perms.add(toUserPermission(perm));
+    }
+    return perms;
+  }
+
+  /**
+   * A utility used to get permissions for selected namespace.
+   * <p>
+   * It's also called by the shell, in case you want to find references.
+   *
+   * @param protocol the AccessControlService protocol proxy
+   * @param namespace name of the namespace
+   * @throws ServiceException
+   */
+  public static List<UserPermission> getUserPermissions(RpcController controller,
+      AccessControlService.BlockingInterface protocol,
+      byte[] namespace) throws ServiceException {
+    AccessControlProtos.GetUserPermissionsRequest.Builder builder =
+        AccessControlProtos.GetUserPermissionsRequest.newBuilder();
+    if (namespace != null) {
+      builder.setNamespaceName(ByteString.copyFrom(namespace));
+    }
+    builder.setType(AccessControlProtos.Permission.Type.Namespace);
+    AccessControlProtos.GetUserPermissionsRequest request = builder.build();
+    AccessControlProtos.GetUserPermissionsResponse response =
+        protocol.getUserPermissions(controller, request);
+    List<UserPermission> perms = new ArrayList<UserPermission>(response.getUserPermissionCount());
+    for (AccessControlProtos.UserPermission perm: response.getUserPermissionList()) {
+      perms.add(toUserPermission(perm));
+    }
+    return perms;
+  }
+
+  /**
+   * Convert a protobuf UserTablePermissions to a
+   * ListMultimap&lt;String, TablePermission&gt; where key is username.
+   *
+   * @param proto the protobuf UserPermission
+   * @return the converted UserPermission
+   */
+  public static ListMultimap<String, TablePermission> toUserTablePermissions(
+      AccessControlProtos.UsersAndPermissions proto) {
+    ListMultimap<String, TablePermission> perms = ArrayListMultimap.create();
+    AccessControlProtos.UsersAndPermissions.UserPermissions userPerm;
+    for (int i = 0; i < proto.getUserPermissionsCount(); i++) {
+      userPerm = proto.getUserPermissions(i);
+      for (int j = 0; j < userPerm.getPermissionsCount(); j++) {
+        TablePermission tablePerm = toTablePermission(userPerm.getPermissions(j));
+        perms.put(userPerm.getUser().toStringUtf8(), tablePerm);
+      }
+    }
+    return perms;
+  }
+
+  /**
+   * Create a request to revoke user permissions.
+   *
+   * @param username the short user name whose permissions to be revoked
+   * @param tableName optional table name the permissions apply
+   * @param family optional column family
+   * @param qualifier optional qualifier
+   * @param actions the permissions to be revoked
+   * @return A {@link AccessControlProtos} RevokeRequest
+   */
+  public static AccessControlProtos.RevokeRequest buildRevokeRequest(
+      String username, TableName tableName, byte[] family, byte[] qualifier,
+      AccessControlProtos.Permission.Action... actions) {
+    AccessControlProtos.Permission.Builder ret =
+        AccessControlProtos.Permission.newBuilder();
+    AccessControlProtos.TablePermission.Builder permissionBuilder =
+        AccessControlProtos.TablePermission.newBuilder();
+    for (AccessControlProtos.Permission.Action a : actions) {
+      permissionBuilder.addAction(a);
+    }
+    if (tableName != null) {
+      permissionBuilder.setTableName(ProtobufUtil.toProtoTableName(tableName));
+    }
+    if (family != null) {
+      permissionBuilder.setFamily(ByteString.copyFrom(family));
+    }
+    if (qualifier != null) {
+      permissionBuilder.setQualifier(ByteString.copyFrom(qualifier));
+    }
+    ret.setType(AccessControlProtos.Permission.Type.Table)
+    .setTablePermission(permissionBuilder);
+    return AccessControlProtos.RevokeRequest.newBuilder()
+        .setUserPermission(
+            AccessControlProtos.UserPermission.newBuilder()
+            .setUser(ByteString.copyFromUtf8(username))
+            .setPermission(ret)
+            ).build();
+  }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/hbase/blob/95c1dc93/hbase-client/src/main/java/org/apache/hadoop/hbase/security/visibility/VisibilityClient.java
----------------------------------------------------------------------
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/security/visibility/VisibilityClient.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/security/visibility/VisibilityClient.java
index 7527049..f6f2dd1 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/security/visibility/VisibilityClient.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/security/visibility/VisibilityClient.java
@@ -32,7 +32,7 @@ import org.apache.hadoop.hbase.client.ConnectionFactory;
 import org.apache.hadoop.hbase.client.Table;
 import org.apache.hadoop.hbase.client.coprocessor.Batch;
 import org.apache.hadoop.hbase.client.security.SecurityCapability;
-import org.apache.hadoop.hbase.ipc.BlockingRpcCallback;
+import org.apache.hadoop.hbase.ipc.CoprocessorRpcUtils;
 import org.apache.hadoop.hbase.ipc.ServerRpcController;
 import org.apache.hadoop.hbase.protobuf.generated.VisibilityLabelsProtos.GetAuthsRequest;
 import org.apache.hadoop.hbase.protobuf.generated.VisibilityLabelsProtos.GetAuthsResponse;
@@ -43,9 +43,9 @@ import org.apache.hadoop.hbase.protobuf.generated.VisibilityLabelsProtos.Visibil
 import org.apache.hadoop.hbase.protobuf.generated.VisibilityLabelsProtos.VisibilityLabelsRequest;
 import org.apache.hadoop.hbase.protobuf.generated.VisibilityLabelsProtos.VisibilityLabelsResponse;
 import org.apache.hadoop.hbase.protobuf.generated.VisibilityLabelsProtos.VisibilityLabelsService;
-import org.apache.hadoop.hbase.util.ByteStringer;
 import org.apache.hadoop.hbase.util.Bytes;
 
+import com.google.protobuf.ByteString;
 import com.google.protobuf.ServiceException;
 
 /**
@@ -128,8 +128,8 @@ public class VisibilityClient {
       Batch.Call<VisibilityLabelsService, VisibilityLabelsResponse> callable =
           new Batch.Call<VisibilityLabelsService, VisibilityLabelsResponse>() {
             ServerRpcController controller = new ServerRpcController();
-            BlockingRpcCallback<VisibilityLabelsResponse> rpcCallback =
-                new BlockingRpcCallback<VisibilityLabelsResponse>();
+            CoprocessorRpcUtils.BlockingRpcCallback<VisibilityLabelsResponse> rpcCallback =
+                new CoprocessorRpcUtils.BlockingRpcCallback<VisibilityLabelsResponse>();
 
             public VisibilityLabelsResponse call(VisibilityLabelsService service)
                 throws IOException {
@@ -137,7 +137,7 @@ public class VisibilityClient {
               for (String label : labels) {
                 if (label.length() > 0) {
                   VisibilityLabel.Builder newBuilder = VisibilityLabel.newBuilder();
-                  newBuilder.setLabel(ByteStringer.wrap(Bytes.toBytes(label)));
+                  newBuilder.setLabel(ByteString.copyFrom(Bytes.toBytes(label)));
                   builder.addVisLabel(newBuilder.build());
                 }
               }
@@ -210,15 +210,15 @@ public class VisibilityClient {
   public static GetAuthsResponse getAuths(Connection connection, final String user)
       throws Throwable {
       try (Table table = connection.getTable(LABELS_TABLE_NAME)) {
-        Batch.Call<VisibilityLabelsService, GetAuthsResponse> callable = 
+        Batch.Call<VisibilityLabelsService, GetAuthsResponse> callable =
             new Batch.Call<VisibilityLabelsService, GetAuthsResponse>() {
           ServerRpcController controller = new ServerRpcController();
-          BlockingRpcCallback<GetAuthsResponse> rpcCallback = 
-              new BlockingRpcCallback<GetAuthsResponse>();
+          CoprocessorRpcUtils.BlockingRpcCallback<GetAuthsResponse> rpcCallback =
+              new CoprocessorRpcUtils.BlockingRpcCallback<GetAuthsResponse>();
 
           public GetAuthsResponse call(VisibilityLabelsService service) throws IOException {
             GetAuthsRequest.Builder getAuthReqBuilder = GetAuthsRequest.newBuilder();
-            getAuthReqBuilder.setUser(ByteStringer.wrap(Bytes.toBytes(user)));
+            getAuthReqBuilder.setUser(ByteString.copyFrom(Bytes.toBytes(user)));
             service.getAuths(controller, getAuthReqBuilder.build(), rpcCallback);
             GetAuthsResponse response = rpcCallback.get();
             if (controller.failedOnException()) {
@@ -266,8 +266,8 @@ public class VisibilityClient {
       Batch.Call<VisibilityLabelsService, ListLabelsResponse> callable =
           new Batch.Call<VisibilityLabelsService, ListLabelsResponse>() {
             ServerRpcController controller = new ServerRpcController();
-            BlockingRpcCallback<ListLabelsResponse> rpcCallback =
-                new BlockingRpcCallback<ListLabelsResponse>();
+            CoprocessorRpcUtils.BlockingRpcCallback<ListLabelsResponse> rpcCallback =
+                new CoprocessorRpcUtils.BlockingRpcCallback<ListLabelsResponse>();
 
             public ListLabelsResponse call(VisibilityLabelsService service) throws IOException {
               ListLabelsRequest.Builder listAuthLabelsReqBuilder = ListLabelsRequest.newBuilder();
@@ -335,18 +335,18 @@ public class VisibilityClient {
           throws IOException, ServiceException, Throwable {
 
       try (Table table = connection.getTable(LABELS_TABLE_NAME)) {
-        Batch.Call<VisibilityLabelsService, VisibilityLabelsResponse> callable = 
+        Batch.Call<VisibilityLabelsService, VisibilityLabelsResponse> callable =
             new Batch.Call<VisibilityLabelsService, VisibilityLabelsResponse>() {
           ServerRpcController controller = new ServerRpcController();
-          BlockingRpcCallback<VisibilityLabelsResponse> rpcCallback = 
-              new BlockingRpcCallback<VisibilityLabelsResponse>();
+          CoprocessorRpcUtils.BlockingRpcCallback<VisibilityLabelsResponse> rpcCallback =
+              new CoprocessorRpcUtils.BlockingRpcCallback<VisibilityLabelsResponse>();
 
           public VisibilityLabelsResponse call(VisibilityLabelsService service) throws IOException {
             SetAuthsRequest.Builder setAuthReqBuilder = SetAuthsRequest.newBuilder();
-            setAuthReqBuilder.setUser(ByteStringer.wrap(Bytes.toBytes(user)));
+            setAuthReqBuilder.setUser(ByteString.copyFrom(Bytes.toBytes(user)));
             for (String auth : auths) {
               if (auth.length() > 0) {
-                setAuthReqBuilder.addAuth(ByteStringer.wrap(Bytes.toBytes(auth)));
+                setAuthReqBuilder.addAuth((ByteString.copyFromUtf8(auth)));
               }
             }
             if (setOrClear) {
@@ -368,4 +368,4 @@ public class VisibilityClient {
         // table and so one entry in result Map.
       }
   }
-}
\ No newline at end of file
+}