1 /* 2 * Copyright (C) 2016 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef _STORAGED_H_ 18 #define _STORAGED_H_ 19 20 #include <semaphore.h> 21 #include <stdint.h> 22 #include <time.h> 23 24 #include <queue> 25 #include <string> 26 #include <unordered_map> 27 #include <vector> 28 29 #include <utils/Mutex.h> 30 31 #include <android/hardware/health/2.0/IHealth.h> 32 33 #define FRIEND_TEST(test_case_name, test_name) \ 34 friend class test_case_name##_##test_name##_Test 35 36 #define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0])) 37 38 #define IS_ALIGNED(x, align) (!((x) & ((align) - 1))) 39 #define ROUND_UP(x, align) (((x) + ((align) - 1)) & ~((align) - 1)) 40 41 #define SECTOR_SIZE ( 512 ) 42 #define SEC_TO_MSEC ( 1000 ) 43 #define MSEC_TO_USEC ( 1000 ) 44 #define USEC_TO_NSEC ( 1000 ) 45 #define SEC_TO_USEC ( 1000000 ) 46 #define HOUR_TO_SEC ( 3600 ) 47 #define DAY_TO_SEC ( 3600 * 24 ) 48 #define WEEK_TO_DAYS ( 7 ) 49 #define YEAR_TO_WEEKS ( 52 ) 50 51 #include "storaged_diskstats.h" 52 #include "storaged_info.h" 53 #include "storaged_uid_monitor.h" 54 #include "storaged.pb.h" 55 #include "uid_info.h" 56 57 using namespace std; 58 using namespace android; 59 60 // Periodic chores intervals in seconds 61 #define DEFAULT_PERIODIC_CHORES_INTERVAL_UNIT ( 60 ) 62 #define DEFAULT_PERIODIC_CHORES_INTERVAL_DISK_STATS_PUBLISH ( 3600 ) 63 #define DEFAULT_PERIODIC_CHORES_INTERVAL_UID_IO ( 3600 ) 64 #define DEFAULT_PERIODIC_CHORES_INTERVAL_UID_IO_LIMIT ( 300 ) 65 #define DEFAULT_PERIODIC_CHORES_INTERVAL_FLUSH_PROTO ( 3600 ) 66 67 // UID IO threshold in bytes 68 #define DEFAULT_PERIODIC_CHORES_UID_IO_THRESHOLD ( 1024 * 1024 * 1024ULL ) 69 70 struct storaged_config { 71 int periodic_chores_interval_unit; 72 int periodic_chores_interval_disk_stats_publish; 73 int periodic_chores_interval_uid_io; 74 int periodic_chores_interval_flush_proto; 75 int event_time_check_usec; // check how much cputime spent in event loop 76 }; 77 78 class storaged_t : public android::hardware::health::V2_0::IHealthInfoCallback, 79 public android::hardware::hidl_death_recipient { 80 private: 81 time_t mTimer; 82 storaged_config mConfig; 83 unique_ptr<disk_stats_monitor> mDsm; 84 uid_monitor mUidm; 85 time_t mStarttime; 86 sp<android::hardware::health::V2_0::IHealth> health; 87 unique_ptr<storage_info_t> storage_info; 88 static const uint32_t current_version; 89 Mutex proto_lock; 90 unordered_map<userid_t, bool> proto_loaded; 91 void load_proto(userid_t user_id); 92 char* prepare_proto(userid_t user_id, StoragedProto* proto); 93 void flush_proto(userid_t user_id, StoragedProto* proto); 94 void flush_proto_data(userid_t user_id, const char* data, ssize_t size); proto_path(userid_t user_id)95 string proto_path(userid_t user_id) { 96 return string("/data/misc_ce/") + to_string(user_id) + 97 "/storaged/storaged.proto"; 98 } 99 void init_health_service(); 100 101 public: 102 storaged_t(void); 103 void init(void); 104 void event(void); 105 void event_checked(void); pause(void)106 void pause(void) { 107 sleep(mConfig.periodic_chores_interval_unit); 108 } 109 get_starttime(void)110 time_t get_starttime(void) { 111 return mStarttime; 112 } 113 get_uids(void)114 unordered_map<uint32_t, uid_info> get_uids(void) { 115 return mUidm.get_uid_io_stats(); 116 } 117 get_perf_history(void)118 vector<int> get_perf_history(void) { 119 return storage_info->get_perf_history(); 120 } 121 get_recent_perf(void)122 uint32_t get_recent_perf(void) { return storage_info->get_recent_perf(); } 123 get_uid_records(double hours,uint64_t threshold,bool force_report)124 map<uint64_t, struct uid_records> get_uid_records( 125 double hours, uint64_t threshold, bool force_report) { 126 return mUidm.dump(hours, threshold, force_report); 127 } 128 update_uid_io_interval(int interval)129 void update_uid_io_interval(int interval) { 130 if (interval >= DEFAULT_PERIODIC_CHORES_INTERVAL_UID_IO_LIMIT) { 131 mConfig.periodic_chores_interval_uid_io = interval; 132 } 133 } 134 135 void add_user_ce(userid_t user_id); 136 void remove_user_ce(userid_t user_id); 137 138 virtual ::android::hardware::Return<void> healthInfoChanged( 139 const ::android::hardware::health::V2_0::HealthInfo& info); 140 void serviceDied(uint64_t cookie, const wp<::android::hidl::base::V1_0::IBase>& who); 141 142 void report_storage_info(); 143 144 void flush_protos(unordered_map<int, StoragedProto>* protos); 145 }; 146 147 // Eventlog tag 148 // The content must match the definition in EventLogTags.logtags 149 #define EVENTLOGTAG_DISKSTATS ( 2732 ) 150 #define EVENTLOGTAG_EMMCINFO ( 2733 ) 151 #define EVENTLOGTAG_UID_IO_ALERT ( 2734 ) 152 153 #endif /* _STORAGED_H_ */ 154