|
every time someone writes a clever thing that Just Works Without Any Code by using intense amounts of reflection it ends up being vulnerable to a million things like this by default which all have to specially patched out, and yet you will never convince anyone that this is a bad way of writing software like yes this should definitely not expose the class but really it should only expose things that opt in to being exposed (and ideally opt in for each specific purpose) and at that point maybe you’re not really getting as much from reflection as you originally dreamed and maybe clients should just be calling into a specifically planned interface
|
# ? Mar 31, 2022 08:30 |
|
|
# ? May 25, 2024 02:39 |
|
Maybe reflection is a bad idea in general
|
# ? Mar 31, 2022 08:31 |
|
I still don't understand what reflection is.
|
# ? Mar 31, 2022 08:55 |
|
Quackles posted:I still don't understand what reflection is. turn your monitor off
|
# ? Mar 31, 2022 09:20 |
|
Quackles posted:I still don't understand what reflection is. you see that class? you can query that class. at runtime!
|
# ? Mar 31, 2022 09:39 |
|
serious answer: in languages like C++ a "class" is more or less a convenient abstraction around some functions and a chunk of memory, once it gets compiled there's not really much information about the structure of the class (in terms of human-readable code structure, anyway) it's all just memory locations and such. in languages like java however a bunch more information about the class gets saved along with it (its fully qualified name, method names, variable names etc.) which means you can then dynamically mess with that information at runtime, to do mundane stuff like determine what specific sub-class an object is if you only know its general parent class, or exciting stuff like "let users pass in arbitrary strings that you then look up against classes to see if that class has the string as a function name, then call the function" it's called reflection because the program can look at itself you see Shame Boy fucked around with this message at 09:48 on Mar 31, 2022 |
# ? Mar 31, 2022 09:46 |
|
rjmccall posted:every time someone writes a clever thing that Just Works Without Any Code by using intense amounts of reflection it ends up being vulnerable to a million things like this by default which all have to specially patched out, and yet you will never convince anyone that this is a bad way of writing software Why where they even motivated to use reflection in this case though? Surely the endpoint knows what data shape it is expecting? (Working out the expected data shape might use reflection but I don't see why that would happen during the http req/res flow)
|
# ? Mar 31, 2022 09:54 |
|
distortion park posted:Why where they even motivated to use reflection in this case though? Surely the endpoint knows what data shape it is expecting? (Working out the expected data shape might use reflection but I don't see why that would happen during the http req/res flow) well what if we make the endpoint dynamically and enterprisely automatedly do different things depending on what type of objects get sent to it and what if we do all this because we can, and never think about how it can be abused
|
# ? Mar 31, 2022 10:07 |
|
distortion park posted:Why where they even motivated to use reflection in this case though? Surely the endpoint knows what data shape it is expecting? (Working out the expected data shape might use reflection but I don't see why that would happen during the http req/res flow) I mean there are legit reasons why you might not know the concrete type e.g. it's implementing an interface and you don't know what sort of IFart it is from inspection and you have to tell the endpoint "this is actually type MyFart", but I'd say that you should make the types available to create limited to explicitly defined implementations only and also not let you call methods arbitrarily either, or in fact at all.
|
# ? Mar 31, 2022 11:56 |
|
Kitfox88 posted:number 2 factor authentication
|
# ? Mar 31, 2022 11:57 |
rafikki posted:yeah, I’m trying to sift through the noise to figure out how seriously to take all this
|
|
# ? Mar 31, 2022 11:57 |
|
Penisface posted:well what if we make the endpoint dynamically and enterprisely automatedly do different things depending on what type of objects get sent to it or ofc you could do this and loudly proclaim your genius at "creating a system where we define the behaviour as config not code" just like all those "generates SQL in the browser and passes it as a string to an exec handler" disaster zones that used to get created
|
# ? Mar 31, 2022 11:58 |
|
distortion park posted:Why where they even motivated to use reflection in this case though? Surely the endpoint knows what data shape it is expecting? (Working out the expected data shape might use reflection but I don't see why that would happen during the http req/res flow) in spring you can just write a http endpoint like this: code:
spring figures all of this out dynamically by examining the structure of the dog object at runtime. If it didn't do this the function would be way longer. Java is staticly typed, it's not like javascript where you can just come up with a dynamically structured object on the spot. You would have to tell java explicitly how to map each property.
|
# ? Mar 31, 2022 12:00 |
|
reflection is everywhere in java land and it's hard to read and annoying for some reason people hate using abstract classes now and the way to call methods on child classes is to by retrieving the method by it's name via reflection and invoking it. why? WHY? this is what abstract classes are for
|
# ? Mar 31, 2022 12:03 |
|
Shame Boy posted:serious answer: in languages like C++ a "class" is more or less a convenient abstraction around some functions and a chunk of memory, once it gets compiled there's not really much information about the structure of the class (in terms of human-readable code structure, anyway) it's all just memory locations and such. in languages like java however a bunch more information about the class gets saved along with it (its fully qualified name, method names, variable names etc.) which means you can then dynamically mess with that information at runtime, to do mundane stuff like determine what specific sub-class an object is if you only know its general parent class, or exciting stuff like "let users pass in arbitrary strings that you then look up against classes to see if that class has the string as a function name, then call the function" my hot take is that language constructs shouldn't really continue to exist in an identifiable way after compilation
|
# ? Mar 31, 2022 12:04 |
|
reflection is what you use when the language design or the framework design say you shouldn't mess with something, but you want to mess with it anyway because you feel like you found a really clever way to do things
|
# ? Mar 31, 2022 14:49 |
|
reflection is good for decoupling, code where every component has to be aware of and relate to the type hierarchy of every other component becomes a mess. it is simultaneously true that one needs to be careful and it should be designed with more concern for security, but pretending that we should just not do it is where you instead start passing around random string serializations or untyped collections of stuff all over the place, and probably ultimately recreating dynamism by doing some even worse eval() garbage.
Cybernetic Vermin fucked around with this message at 15:16 on Mar 31, 2022 |
# ? Mar 31, 2022 15:13 |
|
spankmeister posted:This video explains the whole blockchain game scam (and straight up exploitation of labor) quite well: I can't follow any of this, and I'm sure that's by design.
|
# ? Mar 31, 2022 15:30 |
|
Cybernetic Vermin posted:reflection is good for decoupling, code where every component has to be aware of and relate to the type hierarchy of every other component becomes a mess. it is simultaneously true that one needs to be careful and it should be designed with more concern for security, but pretending that we should just not do it is where you instead start passing around random string serializations or untyped collections of stuff all over the place, and probably ultimately recreating dynamism by doing some even worse eval() garbage. if integration points between different components are allowed to become so finicky that you need reflection or some other magical technology, i would argue that the design is too complex. admittedly i am thinking about REST endpoints here, which in microservice land need to be decoupled so that client/service code can evolve independently. isn’t this why the standard is json/xml for transmitting complex data, and not a magically serialized java object?
|
# ? Mar 31, 2022 15:43 |
|
Penisface posted:if integration points between different components are allowed to become so finicky that you need reflection or some other magical technology, i would argue that the design is too complex. the reason the standard is xml/json is to make it go on a wire, do you figure that in general the solution lies in having less strong typing and encapsulation?
|
# ? Mar 31, 2022 15:47 |
|
Amethyst posted:in spring you can just write a http endpoint like this: I get the role of reflection to simplify the API code, but not why this seems to be used at request handling time (as opposed to at startup time or equivalent). i.e. the expected fields should come from the definition of Dog (which presumably wouldn't include anything other than "name", and is known at startup in theory) rather than from the data that is being sent.
|
# ? Mar 31, 2022 15:59 |
|
Generally you want your code to be using strongly-typed model classes instead of, idk, using a hashmap or some similar kind of bag with strings as keys and you're never really sure whether a given field actually exists or not. To transform a serialised wire format into that strongly-typed class, you basically have three choices: - Hand-written code that transforms the serialised format into your strongly-typed class - A code generator reads your schema and creates ^. Sometimes this also generates your strongly-typed class itself. - A reflective framework that determines at runtime how to fill in your strongly-typed class from the serialised wire format. I generally advocate for the second option, but there are use cases for the other two.
|
# ? Mar 31, 2022 16:01 |
|
Kitfox88 posted:number 2 factor authentication Shamefully overlooked post Cybernetic Vermin posted:reflection is good for decoupling, code where every component has to be aware of and relate to the type hierarchy of every other component becomes a mess. it is simultaneously true that one needs to be careful and it should be designed with more concern for security, but pretending that we should just not do it is where you instead start passing around random string serializations or untyped collections of stuff all over the place, and probably ultimately recreating dynamism by doing some even worse eval() garbage. Reflection is pretty neat, conceptually, though there are obvious security concerns so care needs to be taken. One use case for reflection is to examine a class for a specific attribute, and to allow for annotation based preprocessing. For example, JUnit has the @Before, @After, and @Test annotations, which are the most common ones, although there are others. At runtime, the testing framework can examine every class in the test suite, and determine how to set up / run / tear down the test at runtime. Similarly, dependency injection can be provided for arbitrary classes (see Google Guice); if you can inspect the constrictor for the class, and all of the members with @Inject, you can determine how to build it at runtime. There's annotation preprocessing, which allows for compile time dependency injection like Dagger, but that's another can of worms, especially when debugging. As mentioned above, if you're an idiot, or dealing with 3rd party code, you can inspect otherwise private member contents / functions and change their visibility / invoke them / etc at runtime. This is usually a bad idea, but it might be necessary in certain circumstances. You may be writing a framework that wants to know if certain other plugins do/do not exist in the runtime, without having to know about them at compile time. Think of being able to load all DLLs in a directory; this can be but is not always a good thing. I can create a turd module for your butt framework which is then available at runtime to expose to a user so that they can choose it for the poo poo action, in addition to the Blood and Brick modules that support it. It has perfectly valid reasons to exist, and perfectly valid reasons to not want it to exist. E: JNI, which is how Java communicates back and forth between native code and bytecode, necessarily needs to use reflection due to the nature of running in a VM and thus not being able to just link to the class from native code. JNI is pretty interesting stuff, though that's less reflection and more limited to things you should already know about. Volmarias fucked around with this message at 16:15 on Mar 31, 2022 |
# ? Mar 31, 2022 16:12 |
|
i made people patch some reflection bugs like this at oldjob. they werent happy to do it. i hope they see this news and remember and say "hey thanks achmed"
|
# ? Mar 31, 2022 16:15 |
|
Achmed Jones posted:i made people patch some reflection bugs like this at oldjob. they werent happy to do it. i hope they see this news and remember and say "hey thanks achmed" They won't
|
# ? Mar 31, 2022 16:16 |
|
Volmarias posted:They won't O_O
|
# ? Mar 31, 2022 16:18 |
|
Jabor posted:Generally you want your code to be using strongly-typed model classes instead of, idk, using a hashmap or some similar kind of bag with strings as keys and you're never really sure whether a given field actually exists or not. That's a nice breakdown thanks. I guess my thinking is that a good version of 3 should be basically equivalent to 2, you just define the schema using the language native types rather than starting with a custom schema format. In almost all sensible use cases it shouldn't be using the incoming data as the starting point for deserialization (outside of known discriminator fields)
|
# ? Mar 31, 2022 16:19 |
|
brains posted:turn your monitor off my screen is all scratched up
|
# ? Mar 31, 2022 16:28 |
|
beyond reflection i do wonder how many hilariously huge security bugs hide in dumb use of cglib across the java ecosystem. harder to analyse, but i expect the new interest in this stuff will get there in time. one problem certainly that the tools involved are so blunt (i.e. reflection just breaking into intended-to-be-encapsulated data), but more than that there is so much unprincipled use where it should almost all be wrapped up in a reasonably carefully validated libraries.
|
# ? Mar 31, 2022 16:32 |
|
BattleMaster posted:my hot take is that language constructs shouldn't really continue to exist in an identifiable way after compilation i like that the capybara's back, by the way
|
# ? Mar 31, 2022 18:00 |
|
Jabor posted:Generally you want your code to be using strongly-typed model classes instead of, idk, using a hashmap or some similar kind of bag with strings as keys and you're never really sure whether a given field actually exists or not. java in particular makes it sufficiently trivial to integrate compile-time codegen into your build that doing it at runtime should be an incredibly niche thing. in other languages it's sometimes a nightmare hassle to use codegen and there's a much stronger case for doing it at runtime. distortion park posted:That's a nice breakdown thanks. I guess my thinking is that a good version of 3 should be basically equivalent to 2, you just define the schema using the language native types rather than starting with a custom schema format. In almost all sensible use cases it shouldn't be using the incoming data as the starting point for deserialization (outside of known discriminator fields) where people inevitably run into security problems is when they try to make runtime things which are more flexible than what you can do with compile-time things. suppose instead of taking a concrete class your function takes an IFoo and the deserialization figures out which implementing class to generate. in a codegen-based approach you obviously need to have a fixed set of possible classes at compile time, but in the runtime reflection version you might be tempted to support things like dynamically loading new jar files that contain class definitions if the input json says it should be a concrete type that you don't have loaded. this lets you do all sorts of cool things that you couldn't do otherwise and you can brag about how much more powerful your thing is than the competing library based on codegen, but it also basically always results in giant security problems.
|
# ? Mar 31, 2022 18:36 |
|
whoopsie daisy
|
# ? Mar 31, 2022 20:43 |
|
Shame Boy posted:i like that the capybara's back, by the way I thought the pulp space pirate lady was kind of neat (I got it when a big pile of pulp magazine art was handed out as avatars) but capybaras are obviously the superior subject for avatars
|
# ? Mar 31, 2022 23:36 |
|
As a former enterprise Java developer I want to say that hearing all of your opinions about all of this is incredibly empowering, because these issues were part of what led me to loving hate writing code for a living, and reflect the security concerns I raised while working on and contributing code to open source projects like, uhh, log4j and, er, spring
|
# ? Apr 1, 2022 01:04 |
|
the security industry thanks you for your service
|
# ? Apr 1, 2022 02:59 |
|
brains posted:turn your monitor off
|
# ? Apr 1, 2022 03:54 |
|
akadajet posted:I can't follow any of this, and I'm sure that's by design. yes. all of that stuff exists solely to get you to buy their funny money, because they need more suckers to buy into the scam for them to make money
|
# ? Apr 1, 2022 03:54 |
|
reflection and "hmm i will just investigate this string. ah, a class exists. i will stuff things into it" sounds like a violation of security rule #1, never trust user input granted i also think that the current hyperfocus on microservices for everything is dumb
|
# ? Apr 1, 2022 04:40 |
|
4k dementia
|
# ? Apr 1, 2022 04:43 |
|
|
# ? May 25, 2024 02:39 |
|
if you're deserializing something directly into an interface, you deserve every problem you get
|
# ? Apr 1, 2022 05:33 |