Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(588)

Unified Diff: gcc/gcc/ctrl-intg.c

Issue 2850019: [gcc] Eliminate control integrity pass in favor of nacl instructions generation from the start. (Closed) Base URL: ssh://git@chromiumos-git/nacl-toolchain.git
Patch Set: Created 10 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: gcc/gcc/ctrl-intg.c
diff --git a/gcc/gcc/ctrl-intg.c b/gcc/gcc/ctrl-intg.c
deleted file mode 100644
index 61e10198c5dbe34a1f99332bf8825fcd715c5d93..0000000000000000000000000000000000000000
--- a/gcc/gcc/ctrl-intg.c
+++ /dev/null
@@ -1,376 +0,0 @@
-/* Patch RTL to enforce control flow integrity for GCC.
- Copyright (C) 1987, 1988, 1992, 1997, 1998, 1999, 2000, 2002, 2003,
- 2004, 2005, 2007
- Free Software Foundation, Inc.
-
-This file is part of GCC.
-
-GCC is free software; you can redistribute it and/or modify it under
-the terms of the GNU General Public License as published by the Free
-Software Foundation; either version 3, or (at your option) any later
-version.
-
-GCC is distributed in the hope that it will be useful, but WITHOUT ANY
-WARRANTY; without even the implied warranty of MERCHANTABILITY or
-FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
-for more details.
-
-You should have received a copy of the GNU General Public License
-along with GCC; see the file COPYING3. If not see
-<http://www.gnu.org/licenses/>. */
-
-/* This file is compiled twice: once for the generator programs,
- once for the compiler. */
-#ifdef GENERATOR_FILE
-#include "bconfig.h"
-#else
-#include "config.h"
-#endif
-
-#include "system.h"
-#include "coretypes.h"
-#include "tm.h"
-#include "rtl.h"
-#include "tree-pass.h"
-#include "expr.h"
-
-/* These headers all define things which are not available in
- generator programs. */
-#ifndef GENERATOR_FILE
-#include "tree.h"
-#include "real.h"
-#include "flags.h"
-#include "hard-reg-set.h"
-#include "basic-block.h"
-#endif
-
-static bool
-gate_func (void) {
- return getenv("NACLSHUTDOWN") == NULL;
- /* return flag_control_integrity; */
-}
-
-static void
-process_call_insn(rtx insn) {
- rtx return_value_expr, call_expr, mem_expr, addr_expr, parallel_expr;
- rtx sp_size_expr, tls_disp;
-
- /*
- * Get the expression to be examined from the instruction.
- */
- call_expr = XEXP (insn, 5);
-
- if (GET_CODE (call_expr) == PARALLEL) {
- /*
- * Calls that pop the stack use a PARALLEL containing a CALL and a SET.
- */
- rtx vec1 = XVECEXP (call_expr, 0, 1);
- parallel_expr = call_expr;
- tls_disp = NULL_RTX;
-
- if (TARGET_64BIT &&
- GET_CODE(vec1) == UNSPEC && XINT(vec1, 1) == UNSPEC_TPOFF) {
- /*
- * TLS calls use a PARALLEL containing a CALL and UNSPEC_TPOFF.
- */
- tls_disp = XVECEXP(vec1, 0, 0);
- gcc_assert(GET_CODE(tls_disp) == SYMBOL_REF);
- } else {
- sp_size_expr = XEXP (XEXP (vec1, 1), 1);
- }
- call_expr = XVECEXP (call_expr, 0, 0);
- }
- else {
- parallel_expr = NULL_RTX;
- }
-
- /*
- * Get the call expression and return value (if any).
- */
- if (GET_CODE (call_expr) == SET) {
- /*
- * Functions with return values use a SET instruction wrapper.
- * Get the call out of the set if needed.
- */
- return_value_expr = XEXP (call_expr, 0);
- call_expr = XEXP (call_expr, 1);
- }
- else {
- return_value_expr = NULL_RTX;
- }
-
- /*
- * Extract the target address expression of the function.
- */
- mem_expr = XEXP (call_expr, 0);
-
- /*
- * Get the address expression from the MEM.
- */
-
- gcc_assert (GET_CODE (mem_expr) == MEM);
- addr_expr = XEXP (mem_expr, 0);
-
- if (GET_CODE (addr_expr) != SYMBOL_REF) {
- rtx insns_head, call, call_insn;
- int enable_print;
-
- {
- static int calls_converted=0;
- static int printed=0;
- char* call_limit = getenv("NONACLCALL");
- char* name_compare = getenv("NACLBINS");
- if (name_compare && strcmp(main_input_filename, name_compare) > 0) {
- if (printed == 0) {
- fprintf(stderr, "NACL: name test shut off\n");
- printed = 1;
- }
- return;
- }
-
- ++calls_converted;
- enable_print = (call_limit && calls_converted == atoi(call_limit));
- if (call_limit && calls_converted > atoi(call_limit)) {
- if (printed == 0) {
- fprintf(stderr, "NACL: '%s' call limit exceeded\n",
- main_input_filename);
- printed = 1;
- }
- return;
- }
- /* fprintf(stderr, "NACL: converted call %d\n", calls_converted); */
- }
-
- if (return_value_expr && parallel_expr) {
- if (getenv("NACLDBGBOTH")) return;
- } else if (return_value_expr) {
- if (getenv("NACLDBGRET")) return;
- } else if (parallel_expr) {
- if (getenv("NACLDBGPAR")) return;
- } else {
- if (SIBLING_CALL_P (insn)) {
- if (getenv("NACLDBGNONE1")) return;
- } else {
- char* str = getenv("NACLDBGNONE2");
- if (str) {
- FILE* fp = fopen("/home/sehr/NACLDBGCOUNT", "r+");
- int current_count;
- fscanf(fp, "%d\n", &current_count);
- fprintf(stderr, "NACLDEBUGCOUNT = %d \n", current_count);
- rewind(fp);
- fprintf(fp, "%d\n", current_count+1);
- fclose(fp);
- if (current_count > atoi(str)) {
- fprintf(stderr, "NACLDEBUGCOUNT %d exceeded %d\n",
- current_count, atoi(str));
- return;
- }
- }
- }
- }
-
- start_sequence ();
-
- if (enable_print) {
- fprintf(stderr, "Before:\n");
- print_rtl_single(stderr, insn);
- }
-
- /*
- * Force the called function address to be in a register.
- */
- addr_expr = force_reg (GET_MODE (addr_expr), addr_expr);
-
-#define gen_nacl(suffix) \
- (TARGET_64BIT ? gen_nacl ## suffix ## di : \
- gen_nacl ## suffix ## si)
- /*
- * Generate the appropriate template for the call
- */
- if (return_value_expr && parallel_expr) {
- if (!tls_disp) {
- call = gen_nacl(call_value_pop) (return_value_expr, addr_expr,
- XEXP (call_expr, 1), sp_size_expr);
- } else {
- call = gen_naclcall_tls(mem_expr, XEXP (call_expr, 1));
- }
- } else if (return_value_expr) {
- if (SIBLING_CALL_P (insn)) {
- call = gen_nacl(sibcall_value) (return_value_expr,
- addr_expr, XEXP (call_expr, 1));
- } else {
- call = gen_nacl(call_value) (return_value_expr,
- addr_expr, XEXP (call_expr, 1));
- }
- } else if (parallel_expr) {
- call = gen_nacl(call_pop) (addr_expr, XEXP (call_expr, 1),
- sp_size_expr);
- } else {
- if (SIBLING_CALL_P (insn)) {
- call = gen_nacl(sibcall) (addr_expr, XEXP (call_expr, 1));
- } else {
- call = gen_nacl(call) (addr_expr, XEXP (call_expr, 1));
- }
- }
-
- call_insn = emit_call_insn (call);
-
- RTL_CONST_CALL_P (call_insn) = RTL_CONST_CALL_P (insn);
- RTL_PURE_CALL_P (call_insn) = RTL_PURE_CALL_P (insn);
- SIBLING_CALL_P (call_insn) = SIBLING_CALL_P (insn);
- REG_NOTES (call_insn) = REG_NOTES (insn);
- CALL_INSN_FUNCTION_USAGE (call_insn) = CALL_INSN_FUNCTION_USAGE (insn);
-
- insns_head = get_insns ();
-
- if (enable_print) {
- fprintf(stderr, "After: (%d, %d) \n", RTL_CONST_OR_PURE_CALL_P (call_insn),
- SIBLING_CALL_P (call_insn));
- print_rtl(stderr, insns_head);
- }
-
- end_sequence ();
- emit_insn_before (insns_head, insn);
-
- delete_insn (insn);
- }
-}
-
-
-static void
-process_jump_insn(rtx insn) {
- rtx par_expr, set_expr, addr_expr;
- rtx jmp;
-
- /*
- * Get the contained expression.
- */
- par_expr = XEXP (insn, 5);
-
- if (GET_CODE (par_expr) == PARALLEL) {
- set_expr = XVECEXP (par_expr, 0, 0);
-
- if (GET_CODE (set_expr) == SET) {
- addr_expr = XEXP (set_expr, 1);
-
- if (GET_CODE (addr_expr) == IF_THEN_ELSE) {
- /*
- * Ordinary branches uses parallel/set/if_then_else.
- * Leave them unmodified.
- */
- }
- else {
- /*
- * A table indirect jump instruction has parallel/set/other
- */
- rtx insns_head, jmp_insn;
- int enable_print;
-
- {
- static int calls_converted=0;
- static int printed=0;
- char* name_compare = getenv("NACLBINS");
- char* call_limit = getenv("NONACLJMP");
- if (name_compare && strcmp(main_input_filename, name_compare) > 0) {
- fprintf(stderr, "NACL: name test shut off\n");
- return;
- }
-
- ++calls_converted;
- enable_print = (call_limit && calls_converted == atoi(call_limit));
- if (call_limit && calls_converted > atoi(call_limit)) {
- if (printed == 0) {
- fprintf(stderr, "NACL: '%s' call limit exceeded\n",
- main_input_filename);
- printed = 1;
- }
- return;
- }
- /*fprintf(stderr, "NACL: converted branch %d\n", calls_converted);*/
- }
-
- start_sequence ();
-
- if (enable_print) {
- fprintf(stderr, "Before:\n");
- print_rtl_single(stderr, insn);
- }
- addr_expr = force_reg (GET_MODE (addr_expr), addr_expr);
- jmp = gen_nacl(jmp_table) (addr_expr,
- XEXP (XEXP (XVECEXP (par_expr, 0, 1), 0), 0));
- jmp_insn = emit_jump_insn (jmp);
-
- if (JUMP_LABEL (insn) != NULL_RTX) {
- JUMP_LABEL (jmp_insn) = JUMP_LABEL (insn);
- LABEL_NUSES (JUMP_LABEL (insn))++;
- }
-
- insns_head = get_insns ();
- if (enable_print) {
- fprintf(stderr, "After %p:\n", (void*) JUMP_LABEL (jmp_insn));
- print_rtl(stderr, insns_head);
- }
-
- end_sequence ();
- emit_insn_before (insns_head, insn);
-
- delete_insn (insn);
- }
- }
- } else {
- /*
- * Other indirect jumps remain to be identified.
- */
- }
-}
-
-extern int nacl_special_commands;
-
-static int
-execute_func (void) {
- basic_block bb;
-
- int save_nacl_special_commands = nacl_special_commands;
- nacl_special_commands = 1;
-
- if (getenv("NACLSHUTDOWN4")) return 0;
- /* Even if reload is not yet completed - fake it to make reload impossible */
- FOR_EACH_BB (bb) {
- rtx insn, last;
-
- if (getenv("NACLSHUTDOWN3")) continue;
- for (insn = BB_HEAD (bb), last = NEXT_INSN (BB_END (bb)); insn != last;
- insn = NEXT_INSN(insn)) {
- if (getenv("NACLSHUTDOWN2")) continue;
- if (JUMP_P (insn)) {
- if (flag_control_integrity)
- process_jump_insn (insn);
- }
- if (CALL_P (insn)) {
- if (flag_control_integrity)
- process_call_insn (insn);
- }
- }
- }
-
- nacl_special_commands = save_nacl_special_commands;
- return 0;
-}
-
-struct rtl_opt_pass pass_control_integrity = {
- {
- RTL_PASS,
- "ctrl_intg_insert",
- gate_func,
- execute_func,
- 0, /* sub */
- 0, /* next */
- 0, /* static_pass_number */
- 0, /* tv_id */
- 0, /* properties_required */
- 0, /* properties_provided */
- 0, /* properties_destroyed */
- TODO_dump_func, /* todo_flags_start */
- TODO_dump_func, /* todo_flags_finish */
- }
-};
« gcc/gcc/config/i386/i386.c ('K') | « gcc/gcc/config/i386/i386.md ('k') | gcc/gcc/passes.c » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698