Web developer, open source enthusiast, amateur photographer & Linux user. Blogs @ http://t.co/Xgj1dYR9wb (en) & http://t.co/m0VDEYHnHq (fi)
45 stories
·
1 follower

Firefox Nightly enables support for FIDO U2F Security Keys

2 Shares

This week, Mozilla enabled support for FIDO U2F (Universal 2nd Factor) security keys in the pre-beta release of Firefox, Firefox Nightly. Firefox is the second largest internet browser by user base. In the near future, 80% of the world’s desktop users, including Chrome and Opera users, will benefit from the open authentication standard and YubiKey support out of the box.

When GitHub made support for U2F in 2015, the open source community voted U2F as the most wanted feature in Firefox. We are delighted to now see it happening. Yubico has helped with U2F integration for Firefox and for other platforms and browsers that have or are in the process of making support, as it is critical for taking the YubiKey and U2F unphishable authentication to the global masses.

In today’s world, software installation brings with it not only added complexity for the user, but also the potential risk of malware. Chrome has already enabled millions of websites and services to deploy FIDO U2F seamlessly, mainly through Google and Facebook social login, to help mitigate that. Now with native support for FIDO U2F security keys in Firefox, millions more will benefit from strong, hardware-based two-factor authentication without the need to download or install client software.

Thanks Mozilla for working on increasing security and usability for internet users!

The post Firefox Nightly enables support for FIDO U2F Security Keys appeared first on Yubico.

Read the whole story
miohtama
66 days ago
reply
Helsinki, Finland
iiska
80 days ago
reply
Oulu, Finland
Share this story
Delete

RESTful DOOM

2 Shares

TL;DR I embedded a RESTful API into the classic 1993 game DOOM, allowing the game to be queried and controlled using HTTP and JSON.

“We fully expect to be the number one cause of decreased productivity in businesses around the world.”

   - ID Software press release (1993).


1993

1993 was an exciting year - Sleepless in Seattle opened in theatres, Microsoft shipped Windows NT 3.1, and Whitney Houston’s ‘I Will Always Love You’ was the best selling song for 2 straight months. Oh, and a game called Doom was released!

Doom was created by a small team at ID Software. Wikipedia describes it as one of the most significant and influential titles in video game history, and growing up I loved playing it. As an adult I couldn’t put down a book called Masters of DOOM, which describes the back story of ID Software.

ID Software has a super cool practice of releasing source code for their games. For the kind of hackers who lurk on /r/gamedev, an ID Software engine is an amazing resource to learn from. And lo, in 1997, the Doom engine source code was released, causing much happiness!

2017

I was having trouble finding a fun API to use in a talk I had to do. I had spent the normal amount of time procrastinating and stressing about having to give the talk, and wasn’t making any progress on building a compelling demo.

Late one night, out of the blue, I had the idea to create an API for Doom, now 24 years old(!), and obviously never designed to have an API. I could have some fun digging around the Doom source code and solve my API problem at the same time!

My random idea became RESTful-DOOM - a version of Doom which really does host a RESTful API! The API allows you to query and manipulate various game objects with standard HTTP requests as the game runs.

There were a few challenges:

  • Build an HTTP+JSON RESTful API server in C.
  • Run the server code inside the Doom engine, without breaking the game loop.
  • Figure out what kinds of things we can manipulate in the game world, and how to interact with them in memory to achieve the desired effect!

I choose chocolate-doom as the base Doom code to build on top of. I like this project because it aims to stick as close to the original experience as possible, while making it easy to compile and run on modern systems.

Hosting an HTTP API server inside Doom

chocolate-doom already uses SDL, so I added an -apiport <port> command line arg and used SDLNet_TCP_Open to open a TCP listen socket on startup. Servicing client connections while the game is running is a bit trickier, because the game must continue to update and render the world many times a second, without delay. We must not make any blocking network calls.

The first change I made was to edit D_ProcessEvents (the Doom main loop), to add a call to our new API servicing method API_RunIO. This calls SDLNet_TCP_Accept which accepts a new client, or immediately returns NULL if there are no clients.
If we have a new client, we add its socket to a SocketSet by calling SDLNet_TCP_AddSocket. Being part of a SocketSet allows us to use the non-blocking SDLNet_CheckSockets every tic to determine if there is data available.
If we do have data, API_ParseRequest attempts to parse the data as an HTTP request, using basic C string functions. I used cJSON and yuarel libraries to parse JSON and URI strings respectively.

Routing an HTTP request involves looking at the method and path, then calling the right implementation for the requested action. Below is a snippet from the API_RouteRequest method:

if (strcmp(path, "api/player") == 0)
{
    if (strcmp(method, "PATCH") == 0) 
    {
        return API_PatchPlayer(json_body);
    }
    else if (strcmp(method, "GET") == 0)
    {
        return API_GetPlayer();
    }
    else if (strcmp(method, "DELETE") == 0) {
        return API_DeletePlayer();
    }
    return API_CreateErrorResponse(405, "Method not allowed");
}

Each action implementation (for example API_PatchPlayer) returns an api_response_t containing a status code and JSON response body.

Putting it all together, this is what the call graph looks like when handling a request for PATCH /api/player:

D_ProcessEvents();
  API_RunIO();
    SDLNet_CheckSockets();
    SDLNet_TCP_Recv();
    API_ParseRequest();
    API_RouteRequest();
      API_PatchPlayer();
    API_SendResponse();

Interfacing with Doom entities

Building an API into a game not designed for it is actually quite easy when the game is written in straight C. There are no private fields or class hierarchies to deal with. And the extern keyword makes it easy to reference global Doom variables in our API handling code, even if it feels a bit dirty ;)

cJSON library is used to generate the JSON formatted response data from API calls.

We want the API to provide access to the current map, map objects (scenery, powerups, monsters), doors, and the player. To do these things, we must understand how the Doom engine handles them.

The current episode and map are stored as global int variables. By updating these values, then calling the existing G_DeferedInitNew, we can trigger Doom to switch smoothly to any map and episode we like.

Map objects (mobj_t) implement both scenery items and monsters. I added an id field which gets initialized to a unique value for each new object. This is the id used in the API for routes like /api/world/objects/:id.

To create a new map object, we call the existing P_SpawnMobj with a position and type. This returns us an mobj_t* that we can update with other properties from the API request.

The local player (player_t) is stored in the first index of a global array of players. By updating fields of the player, we can control things like health and weapon used. Behind the scenes, a player is also an mobj_t.

A door in Doom is a line_t with a special door flag. To find all doors, we iterate through all line_t in the map, returning all lines which are marked as a door. To open or close the door, we call the existing EV_VerticalDoor to toggle the door state.

API Specification

An API spec describes the HTTP methods, routes, and data types that the API supports. For example, it will tell you the type of data to send in a POST call to /api/world/objects, and the type of data you should expect in response.
I wrote the API spec in RAML 1.0. It is also hosted in a public API Portal for easier reading.

Putting it all together

So now we have an HTTP+JSON server inside Doom, interfacing with Doom objects in memory, and have written a public API specification for it. Phew!
We can now query and manipulate this 24 year old game from any REST API client - heres a video proving exactly that! Enjoy ;)

restful-doom on GitHub


Read the whole story
iiska
82 days ago
reply
Oulu, Finland
Share this story
Delete

USB Cables

6 Comments and 21 Shares
Tag yourself, I'm "frayed."
Read the whole story
iiska
83 days ago
reply
Oulu, Finland
Share this story
Delete
5 public comments
expatpaul
83 days ago
reply
Painfully true
Belgium
mooglemoogle
83 days ago
reply
I’m “Carries data but not power”
Virginia
CaffieneKitty
82 days ago
I'm "Heavy and not very flexible" :-P
deezil
83 days ago
reply
I need USB-C cables to become cheaper, but basically, if it's not "the good one", it gets thrown in the garbage. Monoprice has them for too cheap to worry about them.
Louisville, Kentucky
alt_text_bot
83 days ago
reply
Tag yourself, I'm "frayed."
endlessmike
79 days ago
Heavy and not very flexible
Covarr
83 days ago
reply
And then there's that weird proprietary cable I've had since like 2004 that looks at a glance like micro USB but isn't, so I get halfway across the country for my vacation with no way to charge anything at all and have to buy spares at the airport for exorbitant prices.
Moses Lake, WA
skittone
83 days ago
Throw it away.
bodly
83 days ago
Or label it.
JimB
79 days ago
My mate threw his away, then wondered why he could no longer connect his Panasonic camera to the computer...

Ringer Volume/Media Volume

9 Comments and 17 Shares
Our new video ad campaign has our product's name shouted in the first 500 milliseconds, so we can reach the people in adjacent rooms while the viewer is still turning down the volume.
Read the whole story
iiska
102 days ago
reply
Oulu, Finland
Share this story
Delete
8 public comments
CaffieneKitty
101 days ago
reply
I have the opposite. I turn my ringer to max and all my morning alarms get turned down to whisper. :-P
rtreborb
101 days ago
reply
The frustration is real
llucax
102 days ago
reply
For UX people out there...
Berlin
ChrisDL
102 days ago
reply
this is me starting twitch while a human being sleeps next to me, trying not to wake her.
New York
mooglemoogle
102 days ago
reply
...Moviefone! If you know the name of the movie you'd like to see....
Virginia
francisga
102 days ago
reply
Yes, happens to me all the time.
Lafayette, LA, USA
alt_text_bot
102 days ago
reply
Our new video ad campaign has our product's name shouted in the first 500 milliseconds, so we can reach the people in adjacent rooms while the viewer is still turning down the volume.
darastar
102 days ago
reply
IT ME!

How to categorize objects

1 Share

How do you categorize software errors?

There are several possible axes we might think of:

  • Severity: e.g. notice, warning, error, fatal.
  • Module: what library or group of classes did the error come from?
  • Layer: database, framework, controller, model, view.

In Exceptional Ruby, I suggested a different approach for categorizing errors. Rather than thinking of different taxonomies that errors might fall into, think about how various types of errors are dealt with. For instance:

  • Inform the user that they tried to use the system in a way that is either not supported or not permitted.
  • Note that the system is in a state that was never planned for, inform the user of a fatal error, and log a problem report back to the developer.
  • Detect a predictable outage, and either retry automatically, or ask the user to manually retry later.

Then, once we have an idea of how different types of errors are handled and/or reported, we can work backwards from these distinctions in order to come up with a set of categories. Which we can then encode as base exception classes:

  • UserError
  • LogicError
  • TransientFailure

Consider a different domain: tasks in a TODO list. Again, there are a lot of ways that these could be categorized: by urgency, by sphere (work, family, personal), by importance.

The GTD system takes a novel tack: it says, “what properties are we most likely going to want to filter by?” The answers it comes up with are:

  • What tasks can I do where I am right now? (Office, kitchen, out running errands)
  • What tasks do I have time for right now?

Working backwards from these questions, it arrives at the idea of categorizing tasks by “context” and by time needed.

These two examples suggest a general pragmatic rule for categorizing objects: don’t worry about listing “natural” taxonomies. Instead, consider how you will most likely need to filter or sort the items.

In some cases, we might not yet know how we might want to filter or sort the objects. In that case, the rule suggests that we hold off on categorizing them at all.

Read the whole story
iiska
149 days ago
reply
Oulu, Finland
Share this story
Delete

A Big Dumb Button

1 Share

Hasselblad2_DEDPXL

My wife Sara and I used to have this running joke leading up to her birthday each year.  Each year I’d say “Honey!  What would you like for your birthday?”

and she would reply “I’d like a Hasselblad”.  Usually with a big smile on her face, in a wink-wink-nudge-nudge kind of way.

Then I’d say “Ha ha, no, seriously, what would you like?” and we’d both laugh and move on to more serious things.

Hasselblad.  The 500c/m.  Man.  That camera.  It’s like the Rolls Royce of cameras.  It would send shivers down our spines and we’d get all giggly any time we’d talk about it.

Hasselblad.  We both wanted one.  For me, the Hasselblad 500c/m is the perfect camera.  It’s this beautiful, perfect melding of function and art mixed together.  It really is a work of art; this little square box and can come all apart and attach to other things to make other types of cameras.  If he was a Transformer he’d be the classiest one.  He’d probably have a swirly moustache and wear a top hat and speak in an elegant accent.

Sometime around 2007-2008 I worked part-time a few days a week at our local camera shop.  Three generations owned this shop.  A downtown staple.  The owner knew everyone that walked in.  He chatted everybody up.  He knew everyones stories.

A few months before Sara’s birthday, this older gentleman came into the shop.  A small, white haired guy, slightly bent over.  He wore one of those blue trucker hats that had the yellow crests on the bill.  It said MARINES.

The owner of the camera store knew of the little ongoing joke that Sara and I had.  Those two were talking for quite a while and as they finished up their conversation, I got called over.

“Sid, this is John.”

“Hi.”

“I told John about your little joke you have with Sara.  John actually works on Hasselblad cameras.”

“You do??” I asked him.

“I do” he said.  “I’m actually about to retire.  I’m going to be closing up my workshop.  I heard about your little run-on gag you have with your lady-friend.  Y’know, I have a bunch of Hasselblad parts at my workshop still.  Let me see if I can piece something together, and if I can, I’ll bring it back in here and we can talk.”

“Oh.  Totally.  That’s awesome.  Thank you.”

And John left the store.  And I figured that even if he did have something lying around, there is no way in hell I’d get my hands on one.  I’d priced them on Craigslist.  I’d followed them on eBay.  Even with the “Great Film Crash” since the advent of digital cameras, the Rolls Royce of cameras was still at a price I couldn’t reach.

 

 

Two days later, John comes walking back in with a plastic bag under his arm.  I got this tingle down my spine.

John pulls a 500c/m out of the bag.  He sets it down on the glass counter and he nods for me to  pick it up.  I paw at it.  It’s beautiful.  It’s all leather and silver streamlined trim.  It’s square and compact. And it’s calling to me.

“Sid.  Sid.  Look at me.  Looooook.”

I wind it, pull the darkslide, and press the shutter.  It makes that beautiful “CLOP-LOMP!” sound.  Oh, that sweet sweet sound.

I owned a Mamiya RB67 while in college.  That thing was a tank.  It was heavy and huge and it was near impossible for me to handhold and take a picture with it.  You could drop an RB from a very tall building and the impact below would make a crater in the ground.  But it would still work.  That camera was fantastic.

But this camera was totally different.  More elegant, refined.  Not cumbersome like a blaster, but refined like a lightsaber.  A more elegant weapon for a more elegant time.  This was the girl that everyone had a crush on.  That everyone wanted to take to the Prom.

 

ProfHasselblad_DEDPXL

This was the one true thing when it came to cameras.

I’m just about to start whispering sweet nothings into it’s viewfinder when John speaks up.  He sounds kinda frustrated and angry.  Not with me, but with himself:

“I was able to piece a kit together.  The leather is good.  The foam inside is clean.  I put a brighter focusing screen in there so you can see better.  It’s in good shape.  But the serial numbers on the body and the film back don’t match.  I hope that’s okay.”

I’m about to get down on my knees and propose marriage and he’s irritated with himself that the serial number don’t match.

“Uh. . .” was all I could say.

I paw at it some more, like a cat playing with a mouse.  All of my logic is gone.  All I can do is oggle the beautiful silver lines that move around the body of this camera.  I’m hypnotized.

“So” John begins and briefly snaps me out of my daydream.

“Here it is” I start thinking.  “The moment he tells me it’s like $1,200 bucks or more and I have to hand it back over to him”.  My brain starts to get depressed.

“I have to ask:  how much?” I say.  I’m a mix of excitement but I’m ever so slightly pulling away because I know I’m going to be ripped away from this beautiful mix of utilitarianism and sculpture.

“Welp, I think it’s great that you both are photographers.  And that you both met in art college.  And I cleaned this thing up just for her.  And since she loves photography and you love photography and she sounds like such a lovely lady, give me $200 and it’s yours.”

I was kind of in a daze.  I had prepared for him to say something close to a thousand.  My body was already instinctively starting to push the camera away from me when he tossed out the price.  It took a few seconds for it to catch up on me.

“Wait, what?”

“Two hundred.  And I might even have a prisim viewfinder back at the workshop.  If I do I’ll bring it by in the next few days.”

 

Nobody has ever seen me run faster out the door of the camera shop, down main street and to the closest ATM.  I ran like the Flash.  I ran for my wife.  I ran for that camera, and in my head, all the pictures I’d take and film I’d wind and times I’d just lovingly look over at it on a tri-pod.

I gave John the cash, and he again told me that if he found a prism for it, he’d bring it by in a few days and I could have it.

Suddenly I looked down and I owned the camera that was in my hand.  Wait.  What?

 

After John left, the owner of the camera store came up to me.  He asked me if I knew who John was.

“No.  He’s a really nice guy that just sold me a dream camera for a steal.” I said.

He told me to go home tonight, and look up the name John Kovacs on the internet.  I might get a better idea of who just left.

So I did.  And I wasn’t prepared for what I found.

 

John Kovacs.

John, it turns out, was one of the original group of technicians that was trained in Sweden many many years ago.  He had been working out of Nashua for decades under the name Hilton Command Exposures.  Back in the days before the Internet, he would be the guy who’s name you would see in the back of camera collector magazines.  He would be the guy that people would recommend to other Hasselblad owners when something went wrong with their camera.  You popped your Hassy in a box and sent it off to Hilton Command Exposures in Nashua NH, and,  weeks or months later,  you’d get your camera back fixed and in perfect working order.  He didn’t have a website.  He worked by word of mouth.

John is the patent holder for the workings that enable multiple exposures on cameras with a film-back mechanism.

And John Kovacs was one of the original group of technicians that worked on the NASA modification of the Hasselblad equipment for the Space Program.

Wait.  What?

Hasselblad_MoonSticker_DEDPXL

Two days later, John came back into the camera store with a prism for me.  I immediately jumped into asking him questions about all this stuff that I found online.

“Yeah” he said with slight irritation “that’s me.”

“Space!  You worked on the cameras that went to the moon!!  That’s amazing!”

John got even more irritated.

“Space.” he dryly said. “Fucking Armstrong couldn’t operate the camera with his big stupid moon gloves on, so I had to create a big dumb button that he could bang to take the exposure.”

It was one of the most surrealistic moments I’ve ever been part of.  Listening to someone irritated about the part they played in documenting people landing on the moon.  There is a whole documentary film in his angry statement.

Shortly after he left.  A week later he retired from being a Hasselblad technician, closed up his shop, sold the rest of his stuff to someone who turned around and sold all of it in pieces on eBay.  The legacy of John Kovacs, and his participation in the history of cameras and photography came to an end.

John moved to Florida to live the remainder of his life happy and retired.  One of the things I regret in our all-too-brief 4 day friendship was not getting a picture of him.  I found a scan of a newspaper article that talked about Hilton Command Exposures back in the early 1990’s.  Sitting there in his workshop, tending to someone’s mail-order, bringing a Rolls Royce of cameras back to life for people all over the world.

 

Sara1DEDPXL

 

Sara was over the moon when she opened her birthday present that year.  And, doubly over the moon when I told her the story that came with the camera.  That some of the most skilled hands refurbed this camera, and that those hands adjusted the camera’s that are still sitting up there on the moon.  And we got one of the very last cameras he worked on before he retired.

John died on January 18, 2013 in North Fort Myers, Florida where he retired. He was a WWII Veteran with the United States Marine Corps. He was formerly the proud owner of Hilton Command Exposures in Nashua.

That camera will never part from us.  It’s too important.  There is too much history behind it.  And one of the things that makes me sad is the history of photography, and of Hasselblad cameras, just became a little less because of John’s passing.  These individuals who are on the outskirts of the history of photography are starting to pass.  While we are obsessed with resolution and cramming megapixels into sensors and how to find the fast track to success, people like John who could turn a camera inside out and back again, are passing on.

I hope the information that was in John’s brain was passed on to somebody.  Or somebodies.  I hope he didn’t die with all the years of technical information and history without being able to pass all that on.  Because I can’t bear knowing that he did.

Share your stories.  Share the stories of those who pass those stories on to you.  Photography is much larger that just taking pictures of things and putting them in a book or on a website.  Share the stories, the conversations that come with them.  Preserve the past and the history, however small it might seem to be.

There is so much more I wish I knew about John.  But I’m glad that I get to share my story about him, however small it might be.

And every time I hear that CLOP-LOMP! coming out of my Hasselblad, I’m preserving John’s legacy and sharing who he was in a minuscule way.

HiltonCommandExposures1992DEDPXL

 

Read the whole story
iiska
162 days ago
reply
Oulu, Finland
Share this story
Delete
Next Page of Stories