Revision: 4428
Author: [email protected]
Date: Thu Apr 15 05:41:30 2010
Log: Add stack alignment check to ia32 and x64
The stack is now checked for proper alignment before calling into C code
when the flag --debug-code is turned on.
Review URL: http://codereview.chromium.org/1637015
http://code.google.com/p/v8/source/detail?r=4428
Modified:
/branches/bleeding_edge/src/ia32/codegen-ia32.cc
/branches/bleeding_edge/src/ia32/macro-assembler-ia32.cc
/branches/bleeding_edge/src/ia32/macro-assembler-ia32.h
/branches/bleeding_edge/src/platform-linux.cc
/branches/bleeding_edge/src/x64/codegen-x64.cc
/branches/bleeding_edge/src/x64/macro-assembler-x64.cc
/branches/bleeding_edge/src/x64/macro-assembler-x64.h
=======================================
--- /branches/bleeding_edge/src/ia32/codegen-ia32.cc Thu Apr 15 02:34:47
2010
+++ /branches/bleeding_edge/src/ia32/codegen-ia32.cc Thu Apr 15 05:41:30
2010
@@ -11739,8 +11739,18 @@
// esi: pointer to the first argument (C callee-saved)
// Result returned in eax, or eax+edx if result_size_ is 2.
+
+ // Check stack alignment.
+ if (FLAG_debug_code) {
+ __ CheckStackAlignment();
+ }
if (do_gc) {
+ // Pass failure code returned from last attempt as first argument to
+ // PerformGC. No need to use PrepareCallCFunction/CallCFunction here
as the
+ // stack alignment is known to be correct. This function takes one
argument
+ // which is passed on the stack, and we know that the stack has been
+ // prepared to pass at least one argument.
__ mov(Operand(esp, 0 * kPointerSize), eax); // Result.
__ call(FUNCTION_ADDR(Runtime::PerformGC), RelocInfo::RUNTIME_ENTRY);
}
=======================================
--- /branches/bleeding_edge/src/ia32/macro-assembler-ia32.cc Wed Apr 14
13:16:19 2010
+++ /branches/bleeding_edge/src/ia32/macro-assembler-ia32.cc Thu Apr 15
05:41:30 2010
@@ -1533,6 +1533,21 @@
// will not return here
bind(&L);
}
+
+
+void MacroAssembler::CheckStackAlignment() {
+ int frame_alignment = OS::ActivationFrameAlignment();
+ int frame_alignment_mask = frame_alignment - 1;
+ if (frame_alignment > kPointerSize) {
+ ASSERT(IsPowerOf2(frame_alignment));
+ Label alignment_as_expected;
+ test(esp, Immediate(frame_alignment_mask));
+ j(zero, &alignment_as_expected);
+ // Abort if stack is not aligned.
+ int3();
+ bind(&alignment_as_expected);
+ }
+}
void MacroAssembler::Abort(const char* msg) {
@@ -1634,6 +1649,11 @@
void MacroAssembler::CallCFunction(Register function,
int num_arguments) {
+ // Check stack alignment.
+ if (FLAG_debug_code) {
+ CheckStackAlignment();
+ }
+
call(Operand(function));
if (OS::ActivationFrameAlignment() != 0) {
mov(esp, Operand(esp, num_arguments * kPointerSize));
=======================================
--- /branches/bleeding_edge/src/ia32/macro-assembler-ia32.h Fri Mar 19
05:01:17 2010
+++ /branches/bleeding_edge/src/ia32/macro-assembler-ia32.h Thu Apr 15
05:41:30 2010
@@ -463,6 +463,9 @@
// Print a message to stdout and abort execution.
void Abort(const char* msg);
+ // Check that the stack is aligned.
+ void CheckStackAlignment();
+
// Verify restrictions about code generated in stubs.
void set_generating_stub(bool value) { generating_stub_ = value; }
bool generating_stub() { return generating_stub_; }
=======================================
--- /branches/bleeding_edge/src/platform-linux.cc Wed Apr 14 11:48:05 2010
+++ /branches/bleeding_edge/src/platform-linux.cc Thu Apr 15 05:41:30 2010
@@ -159,7 +159,7 @@
#elif V8_TARGET_ARCH_MIPS
return 8;
#endif
- // With gcc 4.4 the tree vectorization optimiser can generate code
+ // With gcc 4.4 the tree vectorization optimizer can generate code
// that requires 16 byte alignment such as movdqa on x86.
return 16;
}
=======================================
--- /branches/bleeding_edge/src/x64/codegen-x64.cc Thu Apr 15 02:34:47 2010
+++ /branches/bleeding_edge/src/x64/codegen-x64.cc Thu Apr 15 05:41:30 2010
@@ -8248,9 +8248,17 @@
// Simple results returned in rax (both AMD64 and Win64 calling
conventions).
// Complex results must be written to address passed as first argument.
// AMD64 calling convention: a struct of two pointers in rax+rdx
+
+ // Check stack alignment.
+ if (FLAG_debug_code) {
+ __ CheckStackAlignment();
+ }
if (do_gc) {
- // Pass failure code returned from last attempt as first argument to
GC.
+ // Pass failure code returned from last attempt as first argument to
+ // PerformGC. No need to use PrepareCallCFunction/CallCFunction here
as the
+ // stack is known to be aligned. This function takes one argument
which is
+ // passed in register.
#ifdef _WIN64
__ movq(rcx, rax);
#else // ! defined(_WIN64)
=======================================
--- /branches/bleeding_edge/src/x64/macro-assembler-x64.cc Wed Apr 14
13:16:19 2010
+++ /branches/bleeding_edge/src/x64/macro-assembler-x64.cc Thu Apr 15
05:41:30 2010
@@ -289,6 +289,21 @@
// will not return here
bind(&L);
}
+
+
+void MacroAssembler::CheckStackAlignment() {
+ int frame_alignment = OS::ActivationFrameAlignment();
+ int frame_alignment_mask = frame_alignment - 1;
+ if (frame_alignment > kPointerSize) {
+ ASSERT(IsPowerOf2(frame_alignment));
+ Label alignment_as_expected;
+ testq(rsp, Immediate(frame_alignment_mask));
+ j(zero, &alignment_as_expected);
+ // Abort if stack is not aligned.
+ int3();
+ bind(&alignment_as_expected);
+ }
+}
void MacroAssembler::NegativeZeroTest(Register result,
@@ -2628,6 +2643,11 @@
void MacroAssembler::CallCFunction(Register function, int num_arguments) {
+ // Check stack alignment.
+ if (FLAG_debug_code) {
+ CheckStackAlignment();
+ }
+
call(function);
ASSERT(OS::ActivationFrameAlignment() != 0);
ASSERT(num_arguments >= 0);
=======================================
--- /branches/bleeding_edge/src/x64/macro-assembler-x64.h Tue Apr 13
04:59:37 2010
+++ /branches/bleeding_edge/src/x64/macro-assembler-x64.h Thu Apr 15
05:41:30 2010
@@ -737,6 +737,9 @@
// Print a message to stdout and abort execution.
void Abort(const char* msg);
+ // Check that the stack is aligned.
+ void CheckStackAlignment();
+
// Verify restrictions about code generated in stubs.
void set_generating_stub(bool value) { generating_stub_ = value; }
bool generating_stub() { return generating_stub_; }
--
v8-dev mailing list
[email protected]
http://groups.google.com/group/v8-dev
To unsubscribe, reply using "remove me" as the subject.