am 0feae044: am 46adfa69: Merge "init: Add support "&&" operator in property triggers"
* commit '0feae044f077bd32ba49ef074eacac7d1e704b8f':
init: Add support "&&" operator in property triggers
diff --git a/fastboot/fastboot.c b/fastboot/fastboot.c
index 959d3ad..2dc8ced 100644
--- a/fastboot/fastboot.c
+++ b/fastboot/fastboot.c
@@ -295,9 +295,8 @@
" Can override the fs type and/or\n"
" size the bootloader reports.\n"
" getvar <variable> display a bootloader variable\n"
- " boot <kernel> [ <ramdisk> [ <second> ] ] download and boot kernel\n"
- " flash:raw boot <kernel> [ <ramdisk> [ <second> ] ] create bootimage and \n"
- " flash it\n"
+ " boot <kernel> [ <ramdisk> ] download and boot kernel\n"
+ " flash:raw boot <kernel> [ <ramdisk> ] create bootimage and flash it\n"
" devices list all connected devices\n"
" continue continue with autoboot\n"
" reboot reboot device normally\n"
@@ -325,11 +324,10 @@
}
void *load_bootable_image(const char *kernel, const char *ramdisk,
- const char *secondstage, unsigned *sz,
- const char *cmdline)
+ unsigned *sz, const char *cmdline)
{
- void *kdata = 0, *rdata = 0, *sdata = 0;
- unsigned ksize = 0, rsize = 0, ssize = 0;
+ void *kdata = 0, *rdata = 0;
+ unsigned ksize = 0, rsize = 0;
void *bdata;
unsigned bsize;
@@ -365,18 +363,10 @@
}
}
- if (secondstage) {
- sdata = load_file(secondstage, &ssize);
- if(sdata == 0) {
- fprintf(stderr,"cannot load '%s': %s\n", secondstage, strerror(errno));
- return 0;
- }
- }
-
fprintf(stderr,"creating boot image...\n");
bdata = mkbootimg(kdata, ksize, kernel_offset,
rdata, rsize, ramdisk_offset,
- sdata, ssize, second_offset,
+ 0, 0, second_offset,
page_size, base_addr, tags_offset, &bsize);
if(bdata == 0) {
fprintf(stderr,"failed to create boot.img\n");
@@ -1162,7 +1152,6 @@
} else if(!strcmp(*argv, "boot")) {
char *kname = 0;
char *rname = 0;
- char *sname = 0;
skip(1);
if (argc > 0) {
kname = argv[0];
@@ -1172,11 +1161,7 @@
rname = argv[0];
skip(1);
}
- if (argc > 0) {
- sname = argv[0];
- skip(1);
- }
- data = load_bootable_image(kname, rname, sname, &sz, cmdline);
+ data = load_bootable_image(kname, rname, &sz, cmdline);
if (data == 0) return 1;
fb_queue_download("boot.img", data, sz);
fb_queue_command("boot", "booting");
@@ -1200,18 +1185,14 @@
char *pname = argv[1];
char *kname = argv[2];
char *rname = 0;
- char *sname = 0;
require(3);
- skip(3);
- if (argc > 0) {
- rname = argv[0];
- skip(1);
+ if(argc > 3) {
+ rname = argv[3];
+ skip(4);
+ } else {
+ skip(3);
}
- if (argc > 0) {
- sname = argv[0];
- skip(1);
- }
- data = load_bootable_image(kname, rname, sname, &sz, cmdline);
+ data = load_bootable_image(kname, rname, &sz, cmdline);
if (data == 0) die("cannot load bootable image");
fb_queue_flash(pname, data, sz);
} else if(!strcmp(*argv, "flashall")) {
diff --git a/healthd/healthd.cpp b/healthd/healthd.cpp
index 1fee855..b0002cc 100644
--- a/healthd/healthd.cpp
+++ b/healthd/healthd.cpp
@@ -53,6 +53,7 @@
.batteryCurrentAvgPath = String8(String8::kEmptyString),
.batteryChargeCounterPath = String8(String8::kEmptyString),
.energyCounter = NULL,
+ .boot_min_cap = 0,
.screen_on = NULL,
};
diff --git a/healthd/healthd.h b/healthd/healthd.h
index 4704f0b..84b6d76 100644
--- a/healthd/healthd.h
+++ b/healthd/healthd.h
@@ -67,6 +67,7 @@
android::String8 batteryChargeCounterPath;
int (*energyCounter)(int64_t *);
+ int boot_min_cap;
bool (*screen_on)(android::BatteryProperties *props);
};
diff --git a/healthd/healthd_mode_charger.cpp b/healthd/healthd_mode_charger.cpp
index 9ed5944..8931983 100644
--- a/healthd/healthd_mode_charger.cpp
+++ b/healthd/healthd_mode_charger.cpp
@@ -116,6 +116,7 @@
struct animation *batt_anim;
gr_surface surf_unknown;
+ int boot_min_cap;
};
static struct frame batt_anim_frames[] = {
@@ -520,19 +521,29 @@
LOGW("[%" PRId64 "] booting from charger mode\n", now);
property_set("sys.boot_from_charger_mode", "1");
} else {
- LOGW("[%" PRId64 "] rebooting\n", now);
- android_reboot(ANDROID_RB_RESTART, 0, 0);
+ if (charger->batt_anim->capacity >= charger->boot_min_cap) {
+ LOGW("[%" PRId64 "] rebooting\n", now);
+ android_reboot(ANDROID_RB_RESTART, 0, 0);
+ } else {
+ LOGV("[%lld] ignore power-button press, battery level "
+ "less than minimum\n", now);
+ }
}
} else {
/* if the key is pressed but timeout hasn't expired,
* make sure we wake up at the right-ish time to check
*/
set_next_key_check(charger, key, POWER_ON_KEY_TIME);
+
+ /* Turn on the display and kick animation on power-key press
+ * rather than on key release
+ */
+ kick_animation(charger->batt_anim);
+ request_suspend(false);
}
} else {
/* if the power key got released, force screen state cycle */
if (key->pending) {
- request_suspend(false);
kick_animation(charger->batt_anim);
}
}
@@ -555,6 +566,11 @@
return;
if (!charger->charger_connected) {
+
+ /* Last cycle would have stopped at the extreme top of battery-icon
+ * Need to show the correct level corresponding to capacity.
+ */
+ kick_animation(charger->batt_anim);
request_suspend(false);
if (charger->next_pwr_check == -1) {
charger->next_pwr_check = now + UNPLUGGED_SHUTDOWN_TIME;
@@ -705,4 +721,5 @@
charger->next_key_check = -1;
charger->next_pwr_check = -1;
healthd_config = config;
+ charger->boot_min_cap = config->boot_min_cap;
}
diff --git a/include/system/camera.h b/include/system/camera.h
index 7a4dd53..09c915d 100644
--- a/include/system/camera.h
+++ b/include/system/camera.h
@@ -194,7 +194,12 @@
/** The facing of the camera is opposite to that of the screen. */
CAMERA_FACING_BACK = 0,
/** The facing of the camera is the same as that of the screen. */
- CAMERA_FACING_FRONT = 1
+ CAMERA_FACING_FRONT = 1,
+ /**
+ * The facing of the camera is not fixed relative to the screen.
+ * The cameras with this facing are external cameras, e.g. USB cameras.
+ */
+ CAMERA_FACING_EXTERNAL = 2
};
enum {
diff --git a/init/builtins.c b/init/builtins.c
index b9b5029..303a8ca 100644
--- a/init/builtins.c
+++ b/init/builtins.c
@@ -205,6 +205,68 @@
return -1;
}
+int do_execonce(int nargs, char **args)
+{
+ pid_t child;
+ int child_status = 0;
+ static int already_done;
+
+ if (already_done) {
+ return -1;
+ }
+ already_done = 1;
+ if (!(child = fork())) {
+ /*
+ * Child process.
+ */
+ zap_stdio();
+ char *exec_args[100];
+ int i;
+ int num_process_args = nargs;
+
+ memset(exec_args, 0, sizeof(exec_args));
+ if (num_process_args > ARRAY_SIZE(exec_args) - 1) {
+ ERROR("exec called with %d args, limit is %d", num_process_args,
+ ARRAY_SIZE(exec_args) - 1);
+ _exit(1);
+ }
+ for (i = 1; i < num_process_args; i++)
+ exec_args[i - 1] = args[i];
+
+ if (execv(exec_args[0], exec_args) == -1) {
+ ERROR("Failed to execv '%s' (%s)", exec_args[0], strerror(errno));
+ _exit(1);
+ }
+ ERROR("Returned from execv()!");
+ _exit(1);
+ }
+
+ /*
+ * Parent process.
+ */
+ if (child == -1) {
+ ERROR("Fork failed\n");
+ return -1;
+ }
+
+ if (TEMP_FAILURE_RETRY(waitpid(child, &child_status, 0)) == -1) {
+ ERROR("waitpid(): failed (%s)\n", strerror(errno));
+ return -1;
+ }
+
+ if (WIFSIGNALED(child_status)) {
+ INFO("Child exited due to signal %d\n", WTERMSIG(child_status));
+ return -1;
+ } else if (WIFEXITED(child_status)) {
+ INFO("Child exited normally (exit code %d)\n", WEXITSTATUS(child_status));
+ return WEXITSTATUS(child_status);
+ }
+
+ ERROR("Abnormal child process exit\n");
+
+ return -1;
+}
+
int do_export(int nargs, char **args)
{
return add_environment(args[1], args[2]);
diff --git a/init/init.c b/init/init.c
index d3dd019..096d898 100644
--- a/init/init.c
+++ b/init/init.c
@@ -126,7 +126,7 @@
return -1;
}
-static void zap_stdio(void)
+void zap_stdio(void)
{
int fd;
fd = open("/dev/null", O_RDWR);
diff --git a/init/init.h b/init/init.h
index e03bd53..654a80b 100644
--- a/init/init.h
+++ b/init/init.h
@@ -149,5 +149,6 @@
extern struct selabel_handle *sehandle;
extern struct selabel_handle *sehandle_prop;
extern int selinux_reload_policy(void);
+void zap_stdio(void);
#endif /* _INIT_INIT_H */
diff --git a/init/init_parser.c b/init/init_parser.c
index a124fa2..02cbf3d 100644
--- a/init/init_parser.c
+++ b/init/init_parser.c
@@ -97,6 +97,7 @@
case 'e':
if (!strcmp(s, "nable")) return K_enable;
if (!strcmp(s, "xec")) return K_exec;
+ if (!strcmp(s, "xeconce")) return K_execonce;
if (!strcmp(s, "xport")) return K_export;
break;
case 'g':
diff --git a/init/keywords.h b/init/keywords.h
index 2d97e5b..7473586 100644
--- a/init/keywords.h
+++ b/init/keywords.h
@@ -8,6 +8,7 @@
int do_domainname(int nargs, char **args);
int do_enable(int nargs, char **args);
int do_exec(int nargs, char **args);
+int do_execonce(int nargs, char **args);
int do_export(int nargs, char **args);
int do_hostname(int nargs, char **args);
int do_ifup(int nargs, char **args);
@@ -59,6 +60,7 @@
KEYWORD(domainname, COMMAND, 1, do_domainname)
KEYWORD(enable, COMMAND, 1, do_enable)
KEYWORD(exec, COMMAND, 1, do_exec)
+ KEYWORD(execonce, COMMAND, 1, do_execonce)
KEYWORD(export, COMMAND, 2, do_export)
KEYWORD(group, OPTION, 0, 0)
KEYWORD(hostname, COMMAND, 1, do_hostname)
diff --git a/init/readme.txt b/init/readme.txt
index 0b43fd5..132a869 100644
--- a/init/readme.txt
+++ b/init/readme.txt
@@ -136,10 +136,14 @@
--------
exec <path> [ <argument> ]*
+ This command is not implemented.
+
+execonce <path> [ <argument> ]*
Fork and execute a program (<path>). This will block until
- the program completes execution. It is best to avoid exec
- as unlike the builtin commands, it runs the risk of getting
- init "stuck". (??? maybe there should be a timeout?)
+ the program completes execution. This command can be run at most
+ once during init's lifetime. Subsequent invocations are ignored.
+ It is best to avoid exec as unlike the builtin commands, it runs
+ the risk of getting init "stuck".
export <name> <value>
Set the environment variable <name> equal to <value> in the
diff --git a/libion/ion.c b/libion/ion.c
index 4908932..d1984bd 100644
--- a/libion/ion.c
+++ b/libion/ion.c
@@ -91,6 +91,7 @@
int flags, off_t offset, unsigned char **ptr, int *map_fd)
{
int ret;
+ unsigned char *tmp_ptr;
struct ion_fd_data data = {
.handle = handle,
};
@@ -103,16 +104,17 @@
ret = ion_ioctl(fd, ION_IOC_MAP, &data);
if (ret < 0)
return ret;
- *map_fd = data.fd;
- if (*map_fd < 0) {
+ if (data.fd < 0) {
ALOGE("map ioctl returned negative fd\n");
return -EINVAL;
}
- *ptr = mmap(NULL, length, prot, flags, *map_fd, offset);
- if (*ptr == MAP_FAILED) {
+ tmp_ptr = mmap(NULL, length, prot, flags, data.fd, offset);
+ if (tmp_ptr == MAP_FAILED) {
ALOGE("mmap failed: %s\n", strerror(errno));
return -errno;
}
+ *map_fd = data.fd;
+ *ptr = tmp_ptr;
return ret;
}
@@ -129,11 +131,11 @@
ret = ion_ioctl(fd, ION_IOC_SHARE, &data);
if (ret < 0)
return ret;
- *share_fd = data.fd;
- if (*share_fd < 0) {
+ if (data.fd < 0) {
ALOGE("share ioctl returned negative fd\n");
return -EINVAL;
}
+ *share_fd = data.fd;
return ret;
}
diff --git a/rootdir/init.rc b/rootdir/init.rc
index 32ca673..1b3518d 100644
--- a/rootdir/init.rc
+++ b/rootdir/init.rc
@@ -114,6 +114,10 @@
# set fwmark on accepted sockets
write /proc/sys/net/ipv4/tcp_fwmark_accept 1
+ # disable icmp redirects
+ write /proc/sys/net/ipv4/conf/all/accept_redirects 0
+ write /proc/sys/net/ipv6/conf/all/accept_redirects 0
+
# Create cgroup mount points for process groups
mkdir /dev/cpuctl
mount cgroup none /dev/cpuctl cpu
@@ -523,6 +527,7 @@
onrestart restart zygote
onrestart restart media
onrestart restart surfaceflinger
+ onrestart restart inputflinger
onrestart restart drm
service vold /system/bin/vold
@@ -556,6 +561,12 @@
group graphics drmrpc
onrestart restart zygote
+service inputflinger /system/bin/inputflinger
+ class main
+ user system
+ group input
+ onrestart restart zygote
+
service drm /system/bin/drmserver
class main
user drm