Loading core/java/android/print/PrintAttributes.java +6 −5 Original line number Original line Diff line number Diff line Loading @@ -26,6 +26,7 @@ import android.content.pm.PackageManager.NameNotFoundException; import android.content.res.Resources.NotFoundException; import android.content.res.Resources.NotFoundException; import android.os.Parcel; import android.os.Parcel; import android.os.Parcelable; import android.os.Parcelable; import android.service.print.PrintAttributesProto; import android.text.TextUtils; import android.text.TextUtils; import android.util.ArrayMap; import android.util.ArrayMap; import android.util.ArraySet; import android.util.ArraySet; Loading Loading @@ -54,9 +55,9 @@ public final class PrintAttributes implements Parcelable { @interface ColorMode { @interface ColorMode { } } /** Color mode: Monochrome color scheme, for example one color is used. */ /** Color mode: Monochrome color scheme, for example one color is used. */ public static final int COLOR_MODE_MONOCHROME = 1 << 0; public static final int COLOR_MODE_MONOCHROME = PrintAttributesProto.COLOR_MODE_MONOCHROME; /** Color mode: Color color scheme, for example many colors are used. */ /** Color mode: Color color scheme, for example many colors are used. */ public static final int COLOR_MODE_COLOR = 1 << 1; public static final int COLOR_MODE_COLOR = PrintAttributesProto.COLOR_MODE_COLOR; private static final int VALID_COLOR_MODES = private static final int VALID_COLOR_MODES = COLOR_MODE_MONOCHROME | COLOR_MODE_COLOR; COLOR_MODE_MONOCHROME | COLOR_MODE_COLOR; Loading @@ -69,11 +70,11 @@ public final class PrintAttributes implements Parcelable { @interface DuplexMode { @interface DuplexMode { } } /** Duplex mode: No duplexing. */ /** Duplex mode: No duplexing. */ public static final int DUPLEX_MODE_NONE = 1 << 0; public static final int DUPLEX_MODE_NONE = PrintAttributesProto.DUPLEX_MODE_NONE; /** Duplex mode: Pages are turned sideways along the long edge - like a book. */ /** Duplex mode: Pages are turned sideways along the long edge - like a book. */ public static final int DUPLEX_MODE_LONG_EDGE = 1 << 1; public static final int DUPLEX_MODE_LONG_EDGE = PrintAttributesProto.DUPLEX_MODE_LONG_EDGE; /** Duplex mode: Pages are turned upwards along the short edge - like a notpad. */ /** Duplex mode: Pages are turned upwards along the short edge - like a notpad. */ public static final int DUPLEX_MODE_SHORT_EDGE = 1 << 2; public static final int DUPLEX_MODE_SHORT_EDGE = PrintAttributesProto.DUPLEX_MODE_SHORT_EDGE; private static final int VALID_DUPLEX_MODES = private static final int VALID_DUPLEX_MODES = DUPLEX_MODE_NONE | DUPLEX_MODE_LONG_EDGE | DUPLEX_MODE_SHORT_EDGE; DUPLEX_MODE_NONE | DUPLEX_MODE_LONG_EDGE | DUPLEX_MODE_SHORT_EDGE; Loading core/java/android/print/PrintJobInfo.java +8 −7 Original line number Original line Diff line number Diff line Loading @@ -28,6 +28,7 @@ import android.content.res.Resources; import android.os.Bundle; import android.os.Bundle; import android.os.Parcel; import android.os.Parcel; import android.os.Parcelable; import android.os.Parcelable; import android.service.print.PrintJobInfoProto; import com.android.internal.util.Preconditions; import com.android.internal.util.Preconditions; Loading Loading @@ -88,7 +89,7 @@ public final class PrintJobInfo implements Parcelable { * Next valid states: {@link #STATE_QUEUED} * Next valid states: {@link #STATE_QUEUED} * </p> * </p> */ */ public static final int STATE_CREATED = 1; public static final int STATE_CREATED = PrintJobInfoProto.STATE_CREATED; /** /** * Print job state: The print jobs is created, it is ready * Print job state: The print jobs is created, it is ready Loading @@ -98,7 +99,7 @@ public final class PrintJobInfo implements Parcelable { * {@link #STATE_CANCELED} * {@link #STATE_CANCELED} * </p> * </p> */ */ public static final int STATE_QUEUED = 2; public static final int STATE_QUEUED = PrintJobInfoProto.STATE_QUEUED; /** /** * Print job state: The print job is being printed. * Print job state: The print job is being printed. Loading @@ -107,7 +108,7 @@ public final class PrintJobInfo implements Parcelable { * {@link #STATE_CANCELED}, {@link #STATE_BLOCKED} * {@link #STATE_CANCELED}, {@link #STATE_BLOCKED} * </p> * </p> */ */ public static final int STATE_STARTED = 3; public static final int STATE_STARTED = PrintJobInfoProto.STATE_STARTED; /** /** * Print job state: The print job is blocked. * Print job state: The print job is blocked. Loading @@ -116,7 +117,7 @@ public final class PrintJobInfo implements Parcelable { * {@link #STATE_STARTED} * {@link #STATE_STARTED} * </p> * </p> */ */ public static final int STATE_BLOCKED = 4; public static final int STATE_BLOCKED = PrintJobInfoProto.STATE_BLOCKED; /** /** * Print job state: The print job is successfully printed. * Print job state: The print job is successfully printed. Loading @@ -125,7 +126,7 @@ public final class PrintJobInfo implements Parcelable { * Next valid states: None * Next valid states: None * </p> * </p> */ */ public static final int STATE_COMPLETED = 5; public static final int STATE_COMPLETED = PrintJobInfoProto.STATE_COMPLETED; /** /** * Print job state: The print job was printing but printing failed. * Print job state: The print job was printing but printing failed. Loading @@ -133,7 +134,7 @@ public final class PrintJobInfo implements Parcelable { * Next valid states: {@link #STATE_CANCELED}, {@link #STATE_STARTED} * Next valid states: {@link #STATE_CANCELED}, {@link #STATE_STARTED} * </p> * </p> */ */ public static final int STATE_FAILED = 6; public static final int STATE_FAILED = PrintJobInfoProto.STATE_FAILED; /** /** * Print job state: The print job is canceled. * Print job state: The print job is canceled. Loading @@ -142,7 +143,7 @@ public final class PrintJobInfo implements Parcelable { * Next valid states: None * Next valid states: None * </p> * </p> */ */ public static final int STATE_CANCELED = 7; public static final int STATE_CANCELED = PrintJobInfoProto.STATE_CANCELED; /** The unique print job id. */ /** The unique print job id. */ private PrintJobId mId; private PrintJobId mId; Loading core/java/android/print/PrinterInfo.java +4 −3 Original line number Original line Diff line number Diff line Loading @@ -31,6 +31,7 @@ import android.graphics.drawable.Drawable; import android.graphics.drawable.Icon; import android.graphics.drawable.Icon; import android.os.Parcel; import android.os.Parcel; import android.os.Parcelable; import android.os.Parcelable; import android.service.print.PrinterInfoProto; import android.text.TextUtils; import android.text.TextUtils; import com.android.internal.util.Preconditions; import com.android.internal.util.Preconditions; Loading Loading @@ -59,13 +60,13 @@ public final class PrinterInfo implements Parcelable { public @interface Status { public @interface Status { } } /** Printer status: the printer is idle and ready to print. */ /** Printer status: the printer is idle and ready to print. */ public static final int STATUS_IDLE = 1; public static final int STATUS_IDLE = PrinterInfoProto.STATUS_IDLE; /** Printer status: the printer is busy printing. */ /** Printer status: the printer is busy printing. */ public static final int STATUS_BUSY = 2; public static final int STATUS_BUSY = PrinterInfoProto.STATUS_BUSY; /** Printer status: the printer is not available. */ /** Printer status: the printer is not available. */ public static final int STATUS_UNAVAILABLE = 3; public static final int STATUS_UNAVAILABLE = PrinterInfoProto.STATUS_UNAVAILABLE; private final @NonNull PrinterId mId; private final @NonNull PrinterId mId; Loading core/java/com/android/internal/os/TransferPipe.java +50 −6 Original line number Original line Diff line number Diff line Loading @@ -16,12 +16,8 @@ package com.android.internal.os; package com.android.internal.os; import java.io.Closeable; import android.annotation.NonNull; import java.io.FileDescriptor; import android.annotation.Nullable; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; import android.os.Binder; import android.os.Binder; import android.os.IBinder; import android.os.IBinder; import android.os.IInterface; import android.os.IInterface; Loading @@ -30,6 +26,15 @@ import android.os.RemoteException; import android.os.SystemClock; import android.os.SystemClock; import android.util.Slog; import android.util.Slog; import libcore.io.IoUtils; import java.io.ByteArrayOutputStream; import java.io.Closeable; import java.io.FileDescriptor; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; /** /** * Helper for transferring data through a pipe from a client app. * Helper for transferring data through a pipe from a client app. */ */ Loading Loading @@ -81,6 +86,45 @@ public final class TransferPipe implements Runnable, Closeable { goDump(binder, out, args); goDump(binder, out, args); } } /** * Read raw bytes from a service's dump function. * * <p>This can be used for dumping {@link android.util.proto.ProtoOutputStream protos}. * * @param binder The service providing the data * @param args The arguments passed to the dump function of the service */ public static byte[] dumpAsync(@NonNull IBinder binder, @Nullable String... args) throws IOException, RemoteException { ParcelFileDescriptor[] pipe = ParcelFileDescriptor.createPipe(); try { TransferPipe.dumpAsync(binder, pipe[1].getFileDescriptor(), args); // Data is written completely when dumpAsync is done pipe[1].close(); pipe[1] = null; byte[] buffer = new byte[4096]; try (ByteArrayOutputStream combinedBuffer = new ByteArrayOutputStream()) { try (FileInputStream is = new FileInputStream(pipe[0].getFileDescriptor())) { while (true) { int numRead = is.read(buffer); if (numRead == -1) { break; } combinedBuffer.write(buffer, 0, numRead); } } return combinedBuffer.toByteArray(); } } finally { pipe[0].close(); IoUtils.closeQuietly(pipe[1]); } } static void go(Caller caller, IInterface iface, FileDescriptor out, static void go(Caller caller, IInterface iface, FileDescriptor out, String prefix, String[] args) throws IOException, RemoteException { String prefix, String[] args) throws IOException, RemoteException { go(caller, iface, out, prefix, args, DEFAULT_TIMEOUT); go(caller, iface, out, prefix, args, DEFAULT_TIMEOUT); Loading core/java/com/android/internal/print/DumpUtils.java 0 → 100644 +356 −0 Original line number Original line Diff line number Diff line /* * Copyright (C) 2017 The Android Open Source Project * * Licensed 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 com.android.internal.print; import android.annotation.NonNull; import android.annotation.Nullable; import android.content.ComponentName; import android.content.ComponentNameProto; import android.content.Context; import android.print.PageRange; import android.print.PrintAttributes; import android.print.PrintDocumentInfo; import android.print.PrintJobId; import android.print.PrintJobInfo; import android.print.PrinterCapabilitiesInfo; import android.print.PrinterId; import android.print.PrinterInfo; import android.service.print.MarginsProto; import android.service.print.MediaSizeProto; import android.service.print.PageRangeProto; import android.service.print.PrintAttributesProto; import android.service.print.PrintDocumentInfoProto; import android.service.print.PrintJobInfoProto; import android.service.print.PrinterCapabilitiesProto; import android.service.print.PrinterIdProto; import android.service.print.PrinterInfoProto; import android.service.print.ResolutionProto; import android.util.proto.ProtoOutputStream; /** * Utilities for dumping print related proto buffer */ public class DumpUtils { /** * Write a string to a proto if the string is not {@code null}. * * @param proto The proto to write to * @param id The proto-id of the string * @param string The string to write */ public static void writeStringIfNotNull(@NonNull ProtoOutputStream proto, long id, @Nullable String string) { if (string != null) { proto.write(id, string); } } /** * Write a {@link ComponentName} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param component The component name to write */ public static void writeComponentName(@NonNull ProtoOutputStream proto, long id, @NonNull ComponentName component) { long token = proto.start(id); proto.write(ComponentNameProto.PACKAGE_NAME, component.getPackageName()); proto.write(ComponentNameProto.CLASS_NAME, component.getClassName()); proto.end(token); } /** * Write a {@link PrinterId} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param printerId The printer id to write */ public static void writePrinterId(@NonNull ProtoOutputStream proto, long id, @NonNull PrinterId printerId) { long token = proto.start(id); writeComponentName(proto, PrinterIdProto.SERVICE_NAME, printerId.getServiceName()); proto.write(PrinterIdProto.LOCAL_ID, printerId.getLocalId()); proto.end(token); } /** * Write a {@link PrinterCapabilitiesInfo} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param cap The capabilities to write */ public static void writePrinterCapabilities(@NonNull Context context, @NonNull ProtoOutputStream proto, long id, @NonNull PrinterCapabilitiesInfo cap) { long token = proto.start(id); writeMargins(proto, PrinterCapabilitiesProto.MIN_MARGINS, cap.getMinMargins()); int numMediaSizes = cap.getMediaSizes().size(); for (int i = 0; i < numMediaSizes; i++) { writeMediaSize(context, proto, PrinterCapabilitiesProto.MEDIA_SIZES, cap.getMediaSizes().get(i)); } int numResolutions = cap.getResolutions().size(); for (int i = 0; i < numResolutions; i++) { writeResolution(proto, PrinterCapabilitiesProto.RESOLUTIONS, cap.getResolutions().get(i)); } if ((cap.getColorModes() & PrintAttributes.COLOR_MODE_MONOCHROME) != 0) { proto.write(PrinterCapabilitiesProto.COLOR_MODES, PrintAttributesProto.COLOR_MODE_MONOCHROME); } if ((cap.getColorModes() & PrintAttributes.COLOR_MODE_COLOR) != 0) { proto.write(PrinterCapabilitiesProto.COLOR_MODES, PrintAttributesProto.COLOR_MODE_COLOR); } if ((cap.getDuplexModes() & PrintAttributes.DUPLEX_MODE_NONE) != 0) { proto.write(PrinterCapabilitiesProto.DUPLEX_MODES, PrintAttributesProto.DUPLEX_MODE_NONE); } if ((cap.getDuplexModes() & PrintAttributes.DUPLEX_MODE_LONG_EDGE) != 0) { proto.write(PrinterCapabilitiesProto.DUPLEX_MODES, PrintAttributesProto.DUPLEX_MODE_LONG_EDGE); } if ((cap.getDuplexModes() & PrintAttributes.DUPLEX_MODE_SHORT_EDGE) != 0) { proto.write(PrinterCapabilitiesProto.DUPLEX_MODES, PrintAttributesProto.DUPLEX_MODE_SHORT_EDGE); } proto.end(token); } /** * Write a {@link PrinterInfo} to a proto. * * @param context The context used to resolve resources * @param proto The proto to write to * @param id The proto-id of the component name * @param info The printer info to write */ public static void writePrinterInfo(@NonNull Context context, @NonNull ProtoOutputStream proto, long id, @NonNull PrinterInfo info) { long token = proto.start(id); writePrinterId(proto, PrinterInfoProto.ID, info.getId()); proto.write(PrinterInfoProto.NAME, info.getName()); proto.write(PrinterInfoProto.STATUS, info.getStatus()); proto.write(PrinterInfoProto.DESCRIPTION, info.getDescription()); PrinterCapabilitiesInfo cap = info.getCapabilities(); if (cap != null) { writePrinterCapabilities(context, proto, PrinterInfoProto.CAPABILITIES, cap); } proto.end(token); } /** * Write a {@link PrintAttributes.MediaSize} to a proto. * * @param context The context used to resolve resources * @param proto The proto to write to * @param id The proto-id of the component name * @param mediaSize The media size to write */ public static void writeMediaSize(@NonNull Context context, @NonNull ProtoOutputStream proto, long id, @NonNull PrintAttributes.MediaSize mediaSize) { long token = proto.start(id); proto.write(MediaSizeProto.ID, mediaSize.getId()); proto.write(MediaSizeProto.LABEL, mediaSize.getLabel(context.getPackageManager())); proto.write(MediaSizeProto.HEIGHT_MILS, mediaSize.getHeightMils()); proto.write(MediaSizeProto.WIDTH_MILS, mediaSize.getWidthMils()); proto.end(token); } /** * Write a {@link PrintAttributes.Resolution} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param res The resolution to write */ public static void writeResolution(@NonNull ProtoOutputStream proto, long id, @NonNull PrintAttributes.Resolution res) { long token = proto.start(id); proto.write(ResolutionProto.ID, res.getId()); proto.write(ResolutionProto.LABEL, res.getLabel()); proto.write(ResolutionProto.HORIZONTAL_DPI, res.getHorizontalDpi()); proto.write(ResolutionProto.VERTICAL_DPI, res.getVerticalDpi()); proto.end(token); } /** * Write a {@link PrintAttributes.Margins} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param margins The margins to write */ public static void writeMargins(@NonNull ProtoOutputStream proto, long id, @NonNull PrintAttributes.Margins margins) { long token = proto.start(id); proto.write(MarginsProto.TOP_MILS, margins.getTopMils()); proto.write(MarginsProto.LEFT_MILS, margins.getLeftMils()); proto.write(MarginsProto.RIGHT_MILS, margins.getRightMils()); proto.write(MarginsProto.BOTTOM_MILS, margins.getBottomMils()); proto.end(token); } /** * Write a {@link PrintAttributes} to a proto. * * @param context The context used to resolve resources * @param proto The proto to write to * @param id The proto-id of the component name * @param attributes The attributes to write */ public static void writePrintAttributes(@NonNull Context context, @NonNull ProtoOutputStream proto, long id, @NonNull PrintAttributes attributes) { long token = proto.start(id); PrintAttributes.MediaSize mediaSize = attributes.getMediaSize(); if (mediaSize != null) { writeMediaSize(context, proto, PrintAttributesProto.MEDIA_SIZE, mediaSize); } proto.write(PrintAttributesProto.IS_PORTRAIT, attributes.isPortrait()); PrintAttributes.Resolution res = attributes.getResolution(); if (res != null) { writeResolution(proto, PrintAttributesProto.RESOLUTION, res); } PrintAttributes.Margins minMargins = attributes.getMinMargins(); if (minMargins != null) { writeMargins(proto, PrintAttributesProto.MIN_MARGINS, minMargins); } proto.write(PrintAttributesProto.COLOR_MODE, attributes.getColorMode()); proto.write(PrintAttributesProto.DUPLEX_MODE, attributes.getDuplexMode()); proto.end(token); } /** * Write a {@link PrintDocumentInfo} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param info The info to write */ public static void writePrintDocumentInfo(@NonNull ProtoOutputStream proto, long id, @NonNull PrintDocumentInfo info) { long token = proto.start(id); proto.write(PrintDocumentInfoProto.NAME, info.getName()); int pageCount = info.getPageCount(); if (pageCount != PrintDocumentInfo.PAGE_COUNT_UNKNOWN) { proto.write(PrintDocumentInfoProto.PAGE_COUNT, pageCount); } proto.write(PrintDocumentInfoProto.CONTENT_TYPE, info.getContentType()); proto.write(PrintDocumentInfoProto.DATA_SIZE, info.getDataSize()); proto.end(token); } /** * Write a {@link PageRange} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param range The range to write */ public static void writePageRange(@NonNull ProtoOutputStream proto, long id, @NonNull PageRange range) { long token = proto.start(id); proto.write(PageRangeProto.START, range.getStart()); proto.write(PageRangeProto.END, range.getEnd()); proto.end(token); } /** * Write a {@link PrintJobInfo} to a proto. * * @param context The context used to resolve resources * @param proto The proto to write to * @param id The proto-id of the component name * @param printJobInfo The print job info to write */ public static void writePrintJobInfo(@NonNull Context context, @NonNull ProtoOutputStream proto, long id, @NonNull PrintJobInfo printJobInfo) { long token = proto.start(id); proto.write(PrintJobInfoProto.LABEL, printJobInfo.getLabel()); PrintJobId printJobId = printJobInfo.getId(); if (printJobId != null) { proto.write(PrintJobInfoProto.PRINT_JOB_ID, printJobId.flattenToString()); } int state = printJobInfo.getState(); if (state >= PrintJobInfoProto.STATE_CREATED && state <= PrintJobInfoProto.STATE_CANCELED) { proto.write(PrintJobInfoProto.STATE, state); } else { proto.write(PrintJobInfoProto.STATE, PrintJobInfoProto.STATE_UNKNOWN); } PrinterId printer = printJobInfo.getPrinterId(); if (printer != null) { writePrinterId(proto, PrintJobInfoProto.PRINTER, printer); } String tag = printJobInfo.getTag(); if (tag != null) { proto.write(PrintJobInfoProto.TAG, tag); } proto.write(PrintJobInfoProto.CREATION_TIME, printJobInfo.getCreationTime()); PrintAttributes attributes = printJobInfo.getAttributes(); if (attributes != null) { writePrintAttributes(context, proto, PrintJobInfoProto.ATTRIBUTES, attributes); } PrintDocumentInfo docInfo = printJobInfo.getDocumentInfo(); if (docInfo != null) { writePrintDocumentInfo(proto, PrintJobInfoProto.DOCUMENT_INFO, docInfo); } proto.write(PrintJobInfoProto.IS_CANCELING, printJobInfo.isCancelling()); PageRange[] pages = printJobInfo.getPages(); if (pages != null) { for (int i = 0; i < pages.length; i++) { writePageRange(proto, PrintJobInfoProto.PAGES, pages[i]); } } proto.write(PrintJobInfoProto.HAS_ADVANCED_OPTIONS, printJobInfo.getAdvancedOptions() != null); proto.write(PrintJobInfoProto.PROGRESS, printJobInfo.getProgress()); CharSequence status = printJobInfo.getStatus(context.getPackageManager()); if (status != null) { proto.write(PrintJobInfoProto.STATUS, status.toString()); } proto.end(token); } } Loading
core/java/android/print/PrintAttributes.java +6 −5 Original line number Original line Diff line number Diff line Loading @@ -26,6 +26,7 @@ import android.content.pm.PackageManager.NameNotFoundException; import android.content.res.Resources.NotFoundException; import android.content.res.Resources.NotFoundException; import android.os.Parcel; import android.os.Parcel; import android.os.Parcelable; import android.os.Parcelable; import android.service.print.PrintAttributesProto; import android.text.TextUtils; import android.text.TextUtils; import android.util.ArrayMap; import android.util.ArrayMap; import android.util.ArraySet; import android.util.ArraySet; Loading Loading @@ -54,9 +55,9 @@ public final class PrintAttributes implements Parcelable { @interface ColorMode { @interface ColorMode { } } /** Color mode: Monochrome color scheme, for example one color is used. */ /** Color mode: Monochrome color scheme, for example one color is used. */ public static final int COLOR_MODE_MONOCHROME = 1 << 0; public static final int COLOR_MODE_MONOCHROME = PrintAttributesProto.COLOR_MODE_MONOCHROME; /** Color mode: Color color scheme, for example many colors are used. */ /** Color mode: Color color scheme, for example many colors are used. */ public static final int COLOR_MODE_COLOR = 1 << 1; public static final int COLOR_MODE_COLOR = PrintAttributesProto.COLOR_MODE_COLOR; private static final int VALID_COLOR_MODES = private static final int VALID_COLOR_MODES = COLOR_MODE_MONOCHROME | COLOR_MODE_COLOR; COLOR_MODE_MONOCHROME | COLOR_MODE_COLOR; Loading @@ -69,11 +70,11 @@ public final class PrintAttributes implements Parcelable { @interface DuplexMode { @interface DuplexMode { } } /** Duplex mode: No duplexing. */ /** Duplex mode: No duplexing. */ public static final int DUPLEX_MODE_NONE = 1 << 0; public static final int DUPLEX_MODE_NONE = PrintAttributesProto.DUPLEX_MODE_NONE; /** Duplex mode: Pages are turned sideways along the long edge - like a book. */ /** Duplex mode: Pages are turned sideways along the long edge - like a book. */ public static final int DUPLEX_MODE_LONG_EDGE = 1 << 1; public static final int DUPLEX_MODE_LONG_EDGE = PrintAttributesProto.DUPLEX_MODE_LONG_EDGE; /** Duplex mode: Pages are turned upwards along the short edge - like a notpad. */ /** Duplex mode: Pages are turned upwards along the short edge - like a notpad. */ public static final int DUPLEX_MODE_SHORT_EDGE = 1 << 2; public static final int DUPLEX_MODE_SHORT_EDGE = PrintAttributesProto.DUPLEX_MODE_SHORT_EDGE; private static final int VALID_DUPLEX_MODES = private static final int VALID_DUPLEX_MODES = DUPLEX_MODE_NONE | DUPLEX_MODE_LONG_EDGE | DUPLEX_MODE_SHORT_EDGE; DUPLEX_MODE_NONE | DUPLEX_MODE_LONG_EDGE | DUPLEX_MODE_SHORT_EDGE; Loading
core/java/android/print/PrintJobInfo.java +8 −7 Original line number Original line Diff line number Diff line Loading @@ -28,6 +28,7 @@ import android.content.res.Resources; import android.os.Bundle; import android.os.Bundle; import android.os.Parcel; import android.os.Parcel; import android.os.Parcelable; import android.os.Parcelable; import android.service.print.PrintJobInfoProto; import com.android.internal.util.Preconditions; import com.android.internal.util.Preconditions; Loading Loading @@ -88,7 +89,7 @@ public final class PrintJobInfo implements Parcelable { * Next valid states: {@link #STATE_QUEUED} * Next valid states: {@link #STATE_QUEUED} * </p> * </p> */ */ public static final int STATE_CREATED = 1; public static final int STATE_CREATED = PrintJobInfoProto.STATE_CREATED; /** /** * Print job state: The print jobs is created, it is ready * Print job state: The print jobs is created, it is ready Loading @@ -98,7 +99,7 @@ public final class PrintJobInfo implements Parcelable { * {@link #STATE_CANCELED} * {@link #STATE_CANCELED} * </p> * </p> */ */ public static final int STATE_QUEUED = 2; public static final int STATE_QUEUED = PrintJobInfoProto.STATE_QUEUED; /** /** * Print job state: The print job is being printed. * Print job state: The print job is being printed. Loading @@ -107,7 +108,7 @@ public final class PrintJobInfo implements Parcelable { * {@link #STATE_CANCELED}, {@link #STATE_BLOCKED} * {@link #STATE_CANCELED}, {@link #STATE_BLOCKED} * </p> * </p> */ */ public static final int STATE_STARTED = 3; public static final int STATE_STARTED = PrintJobInfoProto.STATE_STARTED; /** /** * Print job state: The print job is blocked. * Print job state: The print job is blocked. Loading @@ -116,7 +117,7 @@ public final class PrintJobInfo implements Parcelable { * {@link #STATE_STARTED} * {@link #STATE_STARTED} * </p> * </p> */ */ public static final int STATE_BLOCKED = 4; public static final int STATE_BLOCKED = PrintJobInfoProto.STATE_BLOCKED; /** /** * Print job state: The print job is successfully printed. * Print job state: The print job is successfully printed. Loading @@ -125,7 +126,7 @@ public final class PrintJobInfo implements Parcelable { * Next valid states: None * Next valid states: None * </p> * </p> */ */ public static final int STATE_COMPLETED = 5; public static final int STATE_COMPLETED = PrintJobInfoProto.STATE_COMPLETED; /** /** * Print job state: The print job was printing but printing failed. * Print job state: The print job was printing but printing failed. Loading @@ -133,7 +134,7 @@ public final class PrintJobInfo implements Parcelable { * Next valid states: {@link #STATE_CANCELED}, {@link #STATE_STARTED} * Next valid states: {@link #STATE_CANCELED}, {@link #STATE_STARTED} * </p> * </p> */ */ public static final int STATE_FAILED = 6; public static final int STATE_FAILED = PrintJobInfoProto.STATE_FAILED; /** /** * Print job state: The print job is canceled. * Print job state: The print job is canceled. Loading @@ -142,7 +143,7 @@ public final class PrintJobInfo implements Parcelable { * Next valid states: None * Next valid states: None * </p> * </p> */ */ public static final int STATE_CANCELED = 7; public static final int STATE_CANCELED = PrintJobInfoProto.STATE_CANCELED; /** The unique print job id. */ /** The unique print job id. */ private PrintJobId mId; private PrintJobId mId; Loading
core/java/android/print/PrinterInfo.java +4 −3 Original line number Original line Diff line number Diff line Loading @@ -31,6 +31,7 @@ import android.graphics.drawable.Drawable; import android.graphics.drawable.Icon; import android.graphics.drawable.Icon; import android.os.Parcel; import android.os.Parcel; import android.os.Parcelable; import android.os.Parcelable; import android.service.print.PrinterInfoProto; import android.text.TextUtils; import android.text.TextUtils; import com.android.internal.util.Preconditions; import com.android.internal.util.Preconditions; Loading Loading @@ -59,13 +60,13 @@ public final class PrinterInfo implements Parcelable { public @interface Status { public @interface Status { } } /** Printer status: the printer is idle and ready to print. */ /** Printer status: the printer is idle and ready to print. */ public static final int STATUS_IDLE = 1; public static final int STATUS_IDLE = PrinterInfoProto.STATUS_IDLE; /** Printer status: the printer is busy printing. */ /** Printer status: the printer is busy printing. */ public static final int STATUS_BUSY = 2; public static final int STATUS_BUSY = PrinterInfoProto.STATUS_BUSY; /** Printer status: the printer is not available. */ /** Printer status: the printer is not available. */ public static final int STATUS_UNAVAILABLE = 3; public static final int STATUS_UNAVAILABLE = PrinterInfoProto.STATUS_UNAVAILABLE; private final @NonNull PrinterId mId; private final @NonNull PrinterId mId; Loading
core/java/com/android/internal/os/TransferPipe.java +50 −6 Original line number Original line Diff line number Diff line Loading @@ -16,12 +16,8 @@ package com.android.internal.os; package com.android.internal.os; import java.io.Closeable; import android.annotation.NonNull; import java.io.FileDescriptor; import android.annotation.Nullable; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; import android.os.Binder; import android.os.Binder; import android.os.IBinder; import android.os.IBinder; import android.os.IInterface; import android.os.IInterface; Loading @@ -30,6 +26,15 @@ import android.os.RemoteException; import android.os.SystemClock; import android.os.SystemClock; import android.util.Slog; import android.util.Slog; import libcore.io.IoUtils; import java.io.ByteArrayOutputStream; import java.io.Closeable; import java.io.FileDescriptor; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; /** /** * Helper for transferring data through a pipe from a client app. * Helper for transferring data through a pipe from a client app. */ */ Loading Loading @@ -81,6 +86,45 @@ public final class TransferPipe implements Runnable, Closeable { goDump(binder, out, args); goDump(binder, out, args); } } /** * Read raw bytes from a service's dump function. * * <p>This can be used for dumping {@link android.util.proto.ProtoOutputStream protos}. * * @param binder The service providing the data * @param args The arguments passed to the dump function of the service */ public static byte[] dumpAsync(@NonNull IBinder binder, @Nullable String... args) throws IOException, RemoteException { ParcelFileDescriptor[] pipe = ParcelFileDescriptor.createPipe(); try { TransferPipe.dumpAsync(binder, pipe[1].getFileDescriptor(), args); // Data is written completely when dumpAsync is done pipe[1].close(); pipe[1] = null; byte[] buffer = new byte[4096]; try (ByteArrayOutputStream combinedBuffer = new ByteArrayOutputStream()) { try (FileInputStream is = new FileInputStream(pipe[0].getFileDescriptor())) { while (true) { int numRead = is.read(buffer); if (numRead == -1) { break; } combinedBuffer.write(buffer, 0, numRead); } } return combinedBuffer.toByteArray(); } } finally { pipe[0].close(); IoUtils.closeQuietly(pipe[1]); } } static void go(Caller caller, IInterface iface, FileDescriptor out, static void go(Caller caller, IInterface iface, FileDescriptor out, String prefix, String[] args) throws IOException, RemoteException { String prefix, String[] args) throws IOException, RemoteException { go(caller, iface, out, prefix, args, DEFAULT_TIMEOUT); go(caller, iface, out, prefix, args, DEFAULT_TIMEOUT); Loading
core/java/com/android/internal/print/DumpUtils.java 0 → 100644 +356 −0 Original line number Original line Diff line number Diff line /* * Copyright (C) 2017 The Android Open Source Project * * Licensed 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 com.android.internal.print; import android.annotation.NonNull; import android.annotation.Nullable; import android.content.ComponentName; import android.content.ComponentNameProto; import android.content.Context; import android.print.PageRange; import android.print.PrintAttributes; import android.print.PrintDocumentInfo; import android.print.PrintJobId; import android.print.PrintJobInfo; import android.print.PrinterCapabilitiesInfo; import android.print.PrinterId; import android.print.PrinterInfo; import android.service.print.MarginsProto; import android.service.print.MediaSizeProto; import android.service.print.PageRangeProto; import android.service.print.PrintAttributesProto; import android.service.print.PrintDocumentInfoProto; import android.service.print.PrintJobInfoProto; import android.service.print.PrinterCapabilitiesProto; import android.service.print.PrinterIdProto; import android.service.print.PrinterInfoProto; import android.service.print.ResolutionProto; import android.util.proto.ProtoOutputStream; /** * Utilities for dumping print related proto buffer */ public class DumpUtils { /** * Write a string to a proto if the string is not {@code null}. * * @param proto The proto to write to * @param id The proto-id of the string * @param string The string to write */ public static void writeStringIfNotNull(@NonNull ProtoOutputStream proto, long id, @Nullable String string) { if (string != null) { proto.write(id, string); } } /** * Write a {@link ComponentName} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param component The component name to write */ public static void writeComponentName(@NonNull ProtoOutputStream proto, long id, @NonNull ComponentName component) { long token = proto.start(id); proto.write(ComponentNameProto.PACKAGE_NAME, component.getPackageName()); proto.write(ComponentNameProto.CLASS_NAME, component.getClassName()); proto.end(token); } /** * Write a {@link PrinterId} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param printerId The printer id to write */ public static void writePrinterId(@NonNull ProtoOutputStream proto, long id, @NonNull PrinterId printerId) { long token = proto.start(id); writeComponentName(proto, PrinterIdProto.SERVICE_NAME, printerId.getServiceName()); proto.write(PrinterIdProto.LOCAL_ID, printerId.getLocalId()); proto.end(token); } /** * Write a {@link PrinterCapabilitiesInfo} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param cap The capabilities to write */ public static void writePrinterCapabilities(@NonNull Context context, @NonNull ProtoOutputStream proto, long id, @NonNull PrinterCapabilitiesInfo cap) { long token = proto.start(id); writeMargins(proto, PrinterCapabilitiesProto.MIN_MARGINS, cap.getMinMargins()); int numMediaSizes = cap.getMediaSizes().size(); for (int i = 0; i < numMediaSizes; i++) { writeMediaSize(context, proto, PrinterCapabilitiesProto.MEDIA_SIZES, cap.getMediaSizes().get(i)); } int numResolutions = cap.getResolutions().size(); for (int i = 0; i < numResolutions; i++) { writeResolution(proto, PrinterCapabilitiesProto.RESOLUTIONS, cap.getResolutions().get(i)); } if ((cap.getColorModes() & PrintAttributes.COLOR_MODE_MONOCHROME) != 0) { proto.write(PrinterCapabilitiesProto.COLOR_MODES, PrintAttributesProto.COLOR_MODE_MONOCHROME); } if ((cap.getColorModes() & PrintAttributes.COLOR_MODE_COLOR) != 0) { proto.write(PrinterCapabilitiesProto.COLOR_MODES, PrintAttributesProto.COLOR_MODE_COLOR); } if ((cap.getDuplexModes() & PrintAttributes.DUPLEX_MODE_NONE) != 0) { proto.write(PrinterCapabilitiesProto.DUPLEX_MODES, PrintAttributesProto.DUPLEX_MODE_NONE); } if ((cap.getDuplexModes() & PrintAttributes.DUPLEX_MODE_LONG_EDGE) != 0) { proto.write(PrinterCapabilitiesProto.DUPLEX_MODES, PrintAttributesProto.DUPLEX_MODE_LONG_EDGE); } if ((cap.getDuplexModes() & PrintAttributes.DUPLEX_MODE_SHORT_EDGE) != 0) { proto.write(PrinterCapabilitiesProto.DUPLEX_MODES, PrintAttributesProto.DUPLEX_MODE_SHORT_EDGE); } proto.end(token); } /** * Write a {@link PrinterInfo} to a proto. * * @param context The context used to resolve resources * @param proto The proto to write to * @param id The proto-id of the component name * @param info The printer info to write */ public static void writePrinterInfo(@NonNull Context context, @NonNull ProtoOutputStream proto, long id, @NonNull PrinterInfo info) { long token = proto.start(id); writePrinterId(proto, PrinterInfoProto.ID, info.getId()); proto.write(PrinterInfoProto.NAME, info.getName()); proto.write(PrinterInfoProto.STATUS, info.getStatus()); proto.write(PrinterInfoProto.DESCRIPTION, info.getDescription()); PrinterCapabilitiesInfo cap = info.getCapabilities(); if (cap != null) { writePrinterCapabilities(context, proto, PrinterInfoProto.CAPABILITIES, cap); } proto.end(token); } /** * Write a {@link PrintAttributes.MediaSize} to a proto. * * @param context The context used to resolve resources * @param proto The proto to write to * @param id The proto-id of the component name * @param mediaSize The media size to write */ public static void writeMediaSize(@NonNull Context context, @NonNull ProtoOutputStream proto, long id, @NonNull PrintAttributes.MediaSize mediaSize) { long token = proto.start(id); proto.write(MediaSizeProto.ID, mediaSize.getId()); proto.write(MediaSizeProto.LABEL, mediaSize.getLabel(context.getPackageManager())); proto.write(MediaSizeProto.HEIGHT_MILS, mediaSize.getHeightMils()); proto.write(MediaSizeProto.WIDTH_MILS, mediaSize.getWidthMils()); proto.end(token); } /** * Write a {@link PrintAttributes.Resolution} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param res The resolution to write */ public static void writeResolution(@NonNull ProtoOutputStream proto, long id, @NonNull PrintAttributes.Resolution res) { long token = proto.start(id); proto.write(ResolutionProto.ID, res.getId()); proto.write(ResolutionProto.LABEL, res.getLabel()); proto.write(ResolutionProto.HORIZONTAL_DPI, res.getHorizontalDpi()); proto.write(ResolutionProto.VERTICAL_DPI, res.getVerticalDpi()); proto.end(token); } /** * Write a {@link PrintAttributes.Margins} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param margins The margins to write */ public static void writeMargins(@NonNull ProtoOutputStream proto, long id, @NonNull PrintAttributes.Margins margins) { long token = proto.start(id); proto.write(MarginsProto.TOP_MILS, margins.getTopMils()); proto.write(MarginsProto.LEFT_MILS, margins.getLeftMils()); proto.write(MarginsProto.RIGHT_MILS, margins.getRightMils()); proto.write(MarginsProto.BOTTOM_MILS, margins.getBottomMils()); proto.end(token); } /** * Write a {@link PrintAttributes} to a proto. * * @param context The context used to resolve resources * @param proto The proto to write to * @param id The proto-id of the component name * @param attributes The attributes to write */ public static void writePrintAttributes(@NonNull Context context, @NonNull ProtoOutputStream proto, long id, @NonNull PrintAttributes attributes) { long token = proto.start(id); PrintAttributes.MediaSize mediaSize = attributes.getMediaSize(); if (mediaSize != null) { writeMediaSize(context, proto, PrintAttributesProto.MEDIA_SIZE, mediaSize); } proto.write(PrintAttributesProto.IS_PORTRAIT, attributes.isPortrait()); PrintAttributes.Resolution res = attributes.getResolution(); if (res != null) { writeResolution(proto, PrintAttributesProto.RESOLUTION, res); } PrintAttributes.Margins minMargins = attributes.getMinMargins(); if (minMargins != null) { writeMargins(proto, PrintAttributesProto.MIN_MARGINS, minMargins); } proto.write(PrintAttributesProto.COLOR_MODE, attributes.getColorMode()); proto.write(PrintAttributesProto.DUPLEX_MODE, attributes.getDuplexMode()); proto.end(token); } /** * Write a {@link PrintDocumentInfo} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param info The info to write */ public static void writePrintDocumentInfo(@NonNull ProtoOutputStream proto, long id, @NonNull PrintDocumentInfo info) { long token = proto.start(id); proto.write(PrintDocumentInfoProto.NAME, info.getName()); int pageCount = info.getPageCount(); if (pageCount != PrintDocumentInfo.PAGE_COUNT_UNKNOWN) { proto.write(PrintDocumentInfoProto.PAGE_COUNT, pageCount); } proto.write(PrintDocumentInfoProto.CONTENT_TYPE, info.getContentType()); proto.write(PrintDocumentInfoProto.DATA_SIZE, info.getDataSize()); proto.end(token); } /** * Write a {@link PageRange} to a proto. * * @param proto The proto to write to * @param id The proto-id of the component name * @param range The range to write */ public static void writePageRange(@NonNull ProtoOutputStream proto, long id, @NonNull PageRange range) { long token = proto.start(id); proto.write(PageRangeProto.START, range.getStart()); proto.write(PageRangeProto.END, range.getEnd()); proto.end(token); } /** * Write a {@link PrintJobInfo} to a proto. * * @param context The context used to resolve resources * @param proto The proto to write to * @param id The proto-id of the component name * @param printJobInfo The print job info to write */ public static void writePrintJobInfo(@NonNull Context context, @NonNull ProtoOutputStream proto, long id, @NonNull PrintJobInfo printJobInfo) { long token = proto.start(id); proto.write(PrintJobInfoProto.LABEL, printJobInfo.getLabel()); PrintJobId printJobId = printJobInfo.getId(); if (printJobId != null) { proto.write(PrintJobInfoProto.PRINT_JOB_ID, printJobId.flattenToString()); } int state = printJobInfo.getState(); if (state >= PrintJobInfoProto.STATE_CREATED && state <= PrintJobInfoProto.STATE_CANCELED) { proto.write(PrintJobInfoProto.STATE, state); } else { proto.write(PrintJobInfoProto.STATE, PrintJobInfoProto.STATE_UNKNOWN); } PrinterId printer = printJobInfo.getPrinterId(); if (printer != null) { writePrinterId(proto, PrintJobInfoProto.PRINTER, printer); } String tag = printJobInfo.getTag(); if (tag != null) { proto.write(PrintJobInfoProto.TAG, tag); } proto.write(PrintJobInfoProto.CREATION_TIME, printJobInfo.getCreationTime()); PrintAttributes attributes = printJobInfo.getAttributes(); if (attributes != null) { writePrintAttributes(context, proto, PrintJobInfoProto.ATTRIBUTES, attributes); } PrintDocumentInfo docInfo = printJobInfo.getDocumentInfo(); if (docInfo != null) { writePrintDocumentInfo(proto, PrintJobInfoProto.DOCUMENT_INFO, docInfo); } proto.write(PrintJobInfoProto.IS_CANCELING, printJobInfo.isCancelling()); PageRange[] pages = printJobInfo.getPages(); if (pages != null) { for (int i = 0; i < pages.length; i++) { writePageRange(proto, PrintJobInfoProto.PAGES, pages[i]); } } proto.write(PrintJobInfoProto.HAS_ADVANCED_OPTIONS, printJobInfo.getAdvancedOptions() != null); proto.write(PrintJobInfoProto.PROGRESS, printJobInfo.getProgress()); CharSequence status = printJobInfo.getStatus(context.getPackageManager()); if (status != null) { proto.write(PrintJobInfoProto.STATUS, status.toString()); } proto.end(token); } }