Jeff Sharkey 8eebdbe4b5 Interface to dynamically generate DropBox data.
The existing DropBoxManager APIs require that data be entirely
pre-cooked before it can be added.  This adds significant overhead
to Log.wtf() style messages which collect logcat data, since we
need to copy that log data through a pipe to an in-memory buffer.

To avoid that overhead, this change introduces an EntrySource
interface which can either be pre-cooked data or dynamically
generated data written directly to an open FD on disk.  Future
changes will adjust the Log.wtf() logic to use this new interface
to have logcat write directly into an FD.

In addition, this interface paves the way for leveraging a newer
F2FS feature which transparently compresses and decompresses data in
the kernel, instead of forcing us to use DEFLATE in userspace.

This change drops periodic quota checking while recording new
entries, and instead adjusts to pre-flight the quota checks before
writing starts.  It also drops the expensive fsync(), since these
logs are collected on a best-effort basis.

Bug: 176843501
Test: atest CtsDropBoxManagerTestCases
Test: atest FrameworksServicesTests:com.android.server.DropBoxTest
Change-Id: Ic78e99a32cfaf4edac066a73a6864c9c9e9fdeef
2021-01-12 13:51:28 -07:00

102 lines
2.8 KiB
C++

/*
* Copyright (C) 2016 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.
*/
#ifndef _ANDROID_OS_DROPBOXMANAGER_H
#define _ANDROID_OS_DROPBOXMANAGER_H
#include <android-base/unique_fd.h>
#include <binder/Parcel.h>
#include <binder/Parcelable.h>
#include <binder/Status.h>
#include <utils/RefBase.h>
#include <vector>
namespace android {
namespace os {
using namespace android;
using namespace android::base;
using namespace android::binder;
using namespace std;
class DropBoxManager : public virtual RefBase
{
public:
enum {
IS_EMPTY = 1,
IS_TEXT = 2,
IS_GZIPPED = 4
};
DropBoxManager();
virtual ~DropBoxManager();
static sp<DropBoxManager> create();
// Create a new entry with plain text contents.
Status addText(const String16& tag, const string& text);
// Create a new Entry with byte array contents. Makes a copy of the data.
Status addData(const String16& tag, uint8_t const* data, size_t size, int flags);
// Create a new Entry from a file. The file will be opened in this process
// and a handle will be passed to the system process, so no additional permissions
// are required from the system process. Returns NULL if the file can't be opened.
Status addFile(const String16& tag, const string& filename, int flags);
// Create a new Entry from an already opened file. Takes ownership of the
// file descriptor.
Status addFile(const String16& tag, int fd, int flags);
class Entry : public Parcelable {
public:
Entry();
virtual ~Entry();
virtual status_t writeToParcel(Parcel* out) const;
virtual status_t readFromParcel(const Parcel* in);
const vector<uint8_t>& getData() const;
const unique_fd& getFd() const;
int32_t getFlags() const;
int64_t getTimestamp() const;
private:
Entry(const String16& tag, int32_t flags);
Entry(const String16& tag, int32_t flags, int fd);
String16 mTag;
int64_t mTimeMillis;
int32_t mFlags;
vector<uint8_t> mData;
unique_fd mFd;
friend class DropBoxManager;
};
private:
enum {
HAS_BYTE_ARRAY = 8
};
};
}} // namespace android::os
#endif // _ANDROID_OS_DROPBOXMANAGER_H